// Contract: CybrFvcks
// Target function: function stopDutchAuction() external onlyOwner
 an array of `TokenOwnership` structs at `tokenIds` in order.
     * See {ERC721AQueryable-explicitOwnershipOf}
     */
    function explicitOwnershipsOf(uint256[] calldata tokenIds)
        external
        view
        virtual
        override
        returns (TokenOwnership[] memory)
    {
        unchecked {
            uint256 tokenIdsLength = tokenIds.length;
            TokenOwnership[] memory ownerships = new TokenOwnership[](tokenIdsLength);
            for (uint256 i; i != tokenIdsLength; ++i) {
                ownerships[i] = explicitOwnershipOf(tokenIds[i]);
            }
            return ownerships;
        }
    }

    /**
     * @dev Returns an array of token IDs owned by `owner`,
     * in the range [`start`, `stop`)
     * (i.e. `start <= tokenId < stop`).
     *
     * This function allows for tokens to be queried if the collection
     * grows too big for a single call of {ERC721AQueryable-tokensOfOwner}.
     *
     * Requirements:
     *
     * - `start < stop`
     */
    function tokensOfOwnerIn(
        address owner,
        uint256 start,
        uint256 stop
    ) external view virtual override returns (uint256[] memory) {
        unchecked {
            if (start >= stop) revert InvalidQueryRange();
            uint256 tokenIdsIdx;
            uint256 stopLimit = _nextTokenId();
            // Set `start = max(start, _startTokenId())`.
            if (start < _startTokenId()) {
                start = _startTokenId();
            }
            // Set `stop = min(stop, stopLimit)`.
            if (stop > stopLimit) {
                stop = stopLimit;
            }
            uint256 tokenIdsMaxLength = balanceOf(owner);
            // Set `tokenIdsMaxLength = min(balanceOf(owner), stop - start)`,
            // to cater for cases where `balanceOf(owner)` is too big.
            if (start < stop) {
                uint256 rangeLength = stop - start;
                if (rangeLength < tokenIdsMaxLength) {
                    tokenIdsMaxLength = rangeLength;
                }
            } else {
                tokenIdsMaxLength = 0;
            }
            uint256[] memory tokenIds = new uint256[](tokenIdsMaxLength);
            if (tokenIdsMaxLength == 0) {
                return tokenIds;
            }
            // We need to call `explicitOwnershipOf(start)`,
            // because the slot at `start` may not be initialized.
            TokenOwnership memory ownership = explicitOwnershipOf(start);
            address currOwnershipAddr;
            // If the starting slot exists (i.e. not burned), initialize `currOwnershipAddr`.
            // `ownership.address` will not be zero, as `start` is clamped to the valid token ID range.
            if (!ownership.burned) {
                currOwnershipAddr = ownership.addr;
            }
            for (uint256 i = start; i != stop && tokenIdsIdx != tokenIdsMaxLength; ++i) {
                ownership = _ownershipAt(i);
                if (ownership.burned) {
                    continue;
                }
                if (ownership.addr != address(0)) {
                    currOwnershipAddr = ownership.addr;
                }
                if (currOwnershipAddr == owner) {
                    tokenIds[tokenIdsIdx++] = i;
                }
            }
            // Downsize the array to fit.
            assembly {
                mstore(tokenIds, tokenIdsIdx)
            }
            return tokenIds;
        }
    }

    /**
     * @dev Returns an array of token IDs owned by `owner`.
     *
     * This function scans the ownership mapping and is O(`totalSupply`) in complexity.
     * It is meant to be called off-chain.
     *
     * See {ERC721AQueryable-tokensOfOwnerIn} for splitting the scan into
     * multiple smaller scans if the collection is large enough to cause
     * an out-of-gas error (10K collections should be fine).
     */
    function tokensOfOwner(address owner) external view virtual override returns (uint256[] memory) {
        unchecked {
            uint256 tokenIdsIdx;
            address currOwnershipAddr;
            uint256 tokenIdsLength = balanceOf(owner);
            uint256[] memory tokenIds = new uint256[](tokenIdsLength);
            TokenOwnership memory ownership;
            for (uint256 i = _startTokenId(); tokenIdsIdx != tokenIdsLength; ++i) {
                ownership = _ownershipAt(i);
                if (ownership.burned) {
                    continue;
                }
                if (ownership.addr != address(0)) {
                    currOwnershipAddr = ownership.addr;
                }
                if (currOwnershipAddr == owner) {
                    tokenIds[tokenIdsIdx++] = i;
                }
            }
            return tokenIds;
        }
    }
}








pragma solidity ^0.8.12;
abstract contract ERC721AOpensea is
    ERC721AQueryable,
    OperatorFilterer,
    Ownable
{
    bool public operatorFilteringEnabled;

    constructor() {
        _registerForOperatorFiltering();
        operatorFilteringEnabled = true;
    }

    /***************************************************************************
     * Operator Filterer
     */

    function setApprovalForAll(address operator, bool approved)
        public
        override(IERC721A, ERC721A)
        onlyAllowedOperatorApproval(operator)
    {
        super.setApprovalForAll(operator, approved);
    }

    function approve(address operator, uint256 tokenId)
        public
        payable
        override(IERC721A, ERC721A)
        onlyAllowedOperatorApproval(operator)
    {
        super.approve(operator, tokenId);
    }

    function transferFrom(
        address from,
        address to,
        uint256 tokenId
    ) public payable override(IERC721A, ERC721A) onlyAllowedOperator(from) {
        super.transferFrom(from, to, tokenId);
    }

    function safeTransferFrom(
        address from,
        address to,
        uint256 tokenId
    ) public payable override(IERC721A, ERC721A) onlyAllowedOperator(from) {
        super.safeTransferFrom(from, to, tokenId);
    }

    function safeTransferFrom(
        address from,
        address to,
        uint256 tokenId,
        bytes memory data
    ) public payable override(IERC721A, ERC721A) onlyAllowedOperator(from) {
        super.safeTransferFrom(from, to, tokenId, data);
    }

    function supportsInterface(bytes4 interfaceId)
        public
        view
        virtual
        override(IERC721A, ERC721A)
        returns (bool)
    {
        // Supports the following `interfaceId`s:
        // - IERC165: 0x01ffc9a7
        // - IERC721: 0x80ac58cd
        // - IERC721Metadata: 0x5b5e139f
        return ERC721A.supportsInterface(interfaceId);
    }

    function setOperatorFilteringEnabled(bool value) public onlyOwner {
        operatorFilteringEnabled = value;
    }

    function _operatorFilteringEnabled() internal view override returns (bool) {
        return operatorFilteringEnabled;
    }

    function _isPriorityOperator(address operator)
        internal
        pure
        override
        returns (bool)
    {
        // OpenSea Seaport Conduit:
        // https://etherscan.io/address/0x1E0049783F008A0085193E00003D00cd54003c71
        // https://goerli.etherscan.io/address/0x1E0049783F008A0085193E00003D00cd54003c71
        return operator == address(0x1E0049783F008A0085193E00003D00cd54003c71);
    }
}



// *************************************************************************************************************************************************************************************
// *************************************************************************************************************************************************************************************
// *************************************************************************************************************************************************************************************
/*                                                                                                                                                                                                                                                                           
                                             bbbbbbbb                                                                                                                                
        CCCCCCCCCCCCC                        b::::::b                              FFFFFFFFFFFFFFFFFFFFFF                                          kkkkkkkk                          
     CCC::::::::::::C                        b::::::b                              F::::::::::::::::::::F                                          k::::::k                          
   CC:::::::::::::::C                        b::::::b                              F::::::::::::::::::::F                                          k::::::k                          
  C:::::CCCCCCCC::::C                         b:::::b                              FF::::::FFFFFFFFF::::F                                          k::::::k                          
 C:::::C       CCCCCCyyyyyyy           yyyyyyyb:::::bbbbbbbbb    rrrrr   rrrrrrrrr   F:::::F       FFFFFFvvvvvvv           vvvvvvv cccccccccccccccc k:::::k    kkkkkkk  ssssssssss   
C:::::C               y:::::y         y:::::y b::::::::::::::bb  r::::rrr:::::::::r  F:::::F              v:::::v         v:::::vcc:::::::::::::::c k:::::k   k:::::k ss::::::::::s  
C:::::C                y:::::y       y:::::y  b::::::::::::::::b r:::::::::::::::::r F::::::FFFFFFFFFF     v:::::v       v:::::vc:::::::::::::::::c k:::::k  k:::::kss:::::::::::::s 
C:::::C                 y:::::y     y:::::y   b:::::bbbbb:::::::brr::::::rrrrr::::::rF:::::::::::::::F      v:::::v     v:::::vc:::::::cccccc:::::c k:::::k k:::::k s::::::ssss:::::s
C:::::C                  y:::::y   y:::::y    b:::::b    b::::::b r:::::r     r:::::rF:::::::::::::::F       v:::::v   v:::::v c::::::c     ccccccc k::::::k:::::k   s:::::s  ssssss 
C:::::C                   y:::::y y:::::y     b:::::b     b:::::b r:::::r     rrrrrrrF::::::FFFFFFFFFF        v:::::v v:::::v  c:::::c              k:::::::::::k      s::::::s      
C:::::C                    y:::::y:::::y      b:::::b     b:::::b r:::::r            F:::::F                   v:::::v:::::v   c:::::c              k:::::::::::k         s::::::s   
 C:::::C       CCCCCC       y:::::::::y       b:::::b     b:::::b r:::::r            F:::::F                    v:::::::::v    c::::::c     ccccccc k::::::k:::::k  ssssss   s:::::s 
  C:::::CCCCCCCC::::C        y:::::::y        b:::::bbbbbb::::::b r:::::r          FF:::::::FF                   v:::::::v     c:::::::cccccc:::::ck::::::k k:::::k s:::::ssss::::::s
   CC:::::::::::::::C         y:::::y         b::::::::::::::::b  r:::::r          F::::::::FF                    v:::::v       c:::::::::::::::::ck::::::k  k:::::ks::::::::::::::s 
     CCC::::::::::::C        y:::::y          b:::::::::::::::b   r:::::r          F::::::::FF                     v:::v         cc:::::::::::::::ck::::::k   k:::::ks:::::::::::ss  
        CCCCCCCCCCCCC       y:::::y           bbbbbbbbbbbbbbbb    rrrrrrr          FFFFFFFFFFF                      vvv            cccccccccccccccckkkkkkkk    kkkkkkksssssssssss    
                           y:::::y                                                                                                                                                   
                          y:::::y                                                                                                                                                    
                         y:::::y                                                                                                                                                     
                        y:::::y                                                                                                                                                      
                       yyyyyyy    
                                                                                                                                                                                                                               
# ⫙σηiϝέ$t Ἴͳ           
*/                                                                                      
// *************************************************************************************************************************************************************************************
// *************************************************************************************************************************************************************************************
// *************************************************************************************************************************************************************************************

pragma solidity ^0.8.17;
contract CybrFvcks is ERC2981, ReentrancyGuard, Ownable, SteppedDutchAuction, ERC721AOpensea {
  // State Vars
  uint16 public constant AUCTION_SUPPLY = 6900;
  uint8 public constant MAX_TOKENS_AUCTION = 2;
  uint16 public constant FREE_MINT_SUPPLY = 3050;
  uint8 public constant MAX_TOKENS_FREE_MINT_TX = 1;
  uint8 public constant DEV_MINT_SUPPLY = 50;

  uint16 public freeMintedSupply; // Track freeMint() supply
  uint8 public devMintedSupply; // Track devMint() supply

  string private _baseURIextended;
  string public provenance;

  // =============================================================
  //                   CUSTOM ERRORS
  // =============================================================
  /// not accepting mints from contracts on the Dutch Auction
  error NoContractMinting();

  /// Exceeds maximum tokens per transaction
  error ExceedsMaximumTokensPerTransaction();

  /// The wrong ETH value has been sent with a transaction
  error WrongETHValueSent();

  /// refund of excess payment failed
  error RefundFailed();


  // =============================================================
  //                   EVENTS
  // =============================================================
  /**
  * @dev emit when a user mints on the Dutch auction
  * @param userAddress the minting wallet and token recipient
  * @param numberOfTokens the quantity of tokens purchased
  */
  event DutchAuctionMint(address indexed userAddress, uint256 numberOfTokens);


  // =============================================================
  //                   FUNCTIONS
  // =============================================================
  constructor()
    ERC721A("CybrFvcks", "CybrFvcks")
    ERC721AOpensea()
  {
    // TΔΚξ ⨀VξR
  }
  

  // #####################
  // STEPPED DUTCH AUCTION
  // #####################
  /**
  * @notice initialize a new Dutch auction. Price will step down in fixed
  *  amounts, at fixed time intervals, until it hits the final resting price,
  *  where it remains until the auction is ended
  *
  * @dev if the prices do not divide perfectly, the final price step will be
  *  smaller than the rest, i.e. it will stop at finalPrice_.
  *  NOTE calling this multiple times will overwrite the previous parameters.
  *  See {_createNewAuction() in SteppedDutchAuction.sol}
  

  // ====================
  // CREATE DUTCH AUCTION
  //=====================

  * @param startPrice_ starting price in wei
  * @param finalPrice_ final resting price in wei
  * @param priceStep_ incremental price decrease in wei
  * @param timeStepSeconds_ time between each price decrease in seconds
  */
  function createDutchAuction
  (
      uint256 startPrice_, // 69000000000000000 -- 0.069 Ether 
      uint256 finalPrice_, // 10000000000000000 Wei -- 0.01 Ether
      uint256 priceStep_, //  5000000000000000  -- 0.005ETH || 0.000069 Ether = 69000000000000000 Wei
      uint256 timeStepSeconds_ // 300 -- 5min || 10800 -- 3 hrs || 86400 sec -- 24 hrs
  )
      external
      onlyOwner
      nonReentrant
  {
      _createNewAuction(
          startPrice_,
          finalPrice_,
          priceStep_,
          timeStepSeconds_
      );
  }


  // ====================
  // MINT DUTCH AUCTION
  //=====================
  /**
  * @notice Mint tokens on the Dutch auction. To get the current price use
  *  getAuctionPrice().
  * @param numberOfTokens the quantity of tokens to mint
  */
  function mintDutch(uint256 numberOfTokens)
      external
      payable
      isAuctionActive
  {
      require(_totalMinted() + numberOfTokens <= AUCTION_SUPPLY);

      // Ensure caller hasn't already minted a token
      require(balanceOf(msg.sender) <= 2, "per Wallet"); // Check balance

      if (msg.sender != tx.origin) revert NoContractMinting();

      if (numberOfTokens > MAX_TOKENS_AUCTION) {
          revert ExceedsMaximumTokensPerTransaction();
      }

      uint256 price = getAuctionPrice() * numberOfTokens;
      if (msg.value < price) revert WrongETHValueSent();

      _safeMint(msg.sender, numberOfTokens, "");
      emit DutchAuctionMint(msg.sender, numberOfTokens);

      // if the price drops before the tx confirms, the user should pay the
      // amount at tx confirmation.
      if (msg.value > price) {
          (bool success, ) = msg.sender.call{value: (msg.value - price)}("");
          if (!success) revert RefundFailed();
      }
  }


  // ====================
  // START DUTCH AUCTION
  //=====================
  /**
  * @notice start a Dutch Auction that has been set up with
  *  createDutchAuction()
  * @dev See {_startAuction() in SteppedDutchAuction.sol}
  */
  function startDutchAuction() external onlyOwner 
  {
      _startAuction();
  }


  // ====================
  // RESUME DUTCH AUCTION
  //=====================
  /**
  * @dev if a Dutch auction was stopped using stopDutchAuction it can be
  *  resumed with this function. No time is added to the duration so all
  *  elapsed time during the pause is lost.
  *
  * To restart a stopped Dutch auction from the startPrice with its full
  * duration, use _startAuction() again.
  */
  function resumeDutchAuction() external onlyOwner 
  {
      _resumeAuction();
  }


  // ====================
  // STOP DUTCH AUCTION
  //=====================