// File: contracts/imo.sol




// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

/// @title: resolute2023
/// @author: manifold.xyz

import "./manifold/ERC721Creator.sol";

//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//                                                                                                                                                              //
//                                                                                                                                                              //
//    Y7YLLvLvLvL7L7v7v7v7v7v7vvvvvvv7vvv7v7v7v7v7v777777777777777777r777r7r7777777r7r7r77777777777777777r7777v7v7v777v7v777v7v7777777777777v7v7v7v7L7vvLvL7    //
//    Lr77r7r7r7rrr7r7r7r7r7r7r7r7r7r7r7rrr7rrrr;rrrrrir;r;r;rir;r;riririririiiiiii;iiiiiririri;iririr;ririririririr;r;ririririr;r;rrrrrrrrrrrrrr7r7r7r7r77r    //
//    Lrvvv7v777v777v7v7v777v7v7v77777v77777777r77777r7r777r7r7r7r7r7r7rrrrrrrrrrr7rrrrrrr7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r7777777r7r7r777777777777v777v777vr    //
//    777v77777v777v777v7v7777777777r77777r7r7r7r7r7r7rrr7r7r7rrrrrr;rrriririririr;rrr;rrrrrrrrrr7rrrrr7r7r7r7r777r7r7r777777777r77777r7r77777r77777r7777v77    //
//    Lrv7v7v77777777r7r7r777r7r77777r7r7r7rrrrr7r7rrr7rrrrrr;rrrrrrr;riririr;ririririr;rrrirrrrrr7rrrrr7r7r7r7r7r7r7r7r7r7r7r7r7r77777r7r7r7r7r7r777rv7v7vr    //
//    777v7v7777r7777777r77777r7r7r7r7rrr7r7r7r7rrrrrr;rrrrrrr;rirrrir;ririririiiririririrrrrrrrrrrrrrrrrrr7r7r7r7r7r7r7r7r7r7r777r7r7r7r7r7r7r7r777r7777v77    //
//    vrv77777777r7r777r7r7rrr7r7r7r7r7r7r7r7rrrr;rrrrr;rrrrriririr;r;ri;iii;i;i;i;ir;r;rirrrrrrrrrrrrrrrrrrrr7rrr7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r777777vr    //
//    7r7777r7rrr7r7r7r7r7rrr7r7r7r7r7rrr7rrrr;rrrrrrr;rrri;iriririririiiriii;iii;iiirir;rirrr;rrr;ri;irrrr7r7r7r7r7r7r7r7r7r7r7r7r7r777r7r7r7r777r7r7777v77    //
//    7r7r7r7rrr7r7rrr7r7rrr7r7r7r7r7r7rrrrrrrrrr;rrr;r;ri;;rir;ri;iri;i;iiiiiiiiiiiiiiir;rrr;riririrrrrrr7rrr7r7r7rrr7r7r7r7r7r7rrr7r7r7r7r7r7r7r7r777777vr    //
//    rrr7r7r7r7rrr7r7r7r7r7rrr7rrr7rrr7rrrrr7rrrrrrrr;ririri;iii;i;iiiiiiiiiiiiiiiii;i;ir;;iri;irrrr7rrrrrririrr7r7r7rrrrr7r7r7r7r7r7r7r7r7r7r7r7r7r7r7r77r    //
//    7;7r7r7rrr7rrr7r7r7r7rrr7rrrrrr;r;r;r;r;r;r;riririri;iriii;iiiiiiiiiiiiii:iiiiii;iiiiiii;ir;;iiiiii:ii;irir;r;rr7r7rrr7r7r7r7r7r7rrr7r7rrrrr7r7r7r77vr    //
//    7rr7rrrrrrrrr7rrrrrrrrrrrrrr;rrr;rrr;r;rrr;r;riri;i;i;i;i;iiiiiiiiiiii:i:::i:i:iiiii:i:i:::::::::i:i:i:i:iiiiiirrrrrrrrrrririr;rr7rrrrr7r7r7rrr7r7r7rr    //
//    7i7rr;rrr;rrrrrrr;r;rrr;rrrrrrrrrrrrrrrrr;r;ri;i;i;iriiiiiiiiiiiiii:i:i:i:::::::::i::,:,:,:,::::::::::iiri;ir;riri;iii;iiiririr;rrrrrrrrrrrr7r7r7r7r7i    //
//    rirrrr;r;rrr;r;r;r;rrrrr;rrrrrrrrrrrrr;rrr;ririri;i;i;iiiiiiiiii:i:i:i:i:::::::i:::::::::::::i:i:i:iiri;iii;iii;iiiri;rr;r;rrrrr;rrr;r;rrrrr;rr7rrr7rr    //
//    rir;ririr;rir;rrrrrrrrr;rrr;rir;r;r;rrr;riri;iiiiii:i:::::::::::::::::::::::::i:i:i:iiiiiiriiiiiiiiiiiiiiiiirir;r;r;rrriririr;r;riririr;rir;r;r;rrrr7i    //
//    ri;r;ririririr;rrr;rir;r;rir;ririri;iiiiii:i:i:i:::::::::i:i:i:i:i:::::::::::::i:i:iiiiiiiiiiiiiiiiiiiiiiii;iiiiiii;i;i;i;i;i;i;iriririr;r;ririrrrrrr;    //
//    7ir;ririr;ririr;ririii;i;iriii;i;iiiiii:::::::::::::iii:i:iii:i:i:::::::::::::::::::::::::i:::i:i:i:i:iiiiiiiiiiii;i;i;irir;ririr;rir;rir;r;rirrrrrrri    //
//    rirriri;iririiiiiiiiii:iii:iiiiiiiiiiiii:i:i:iiiii:i:i:i:i::::::::::,:,,,,.,,,,:,::::::::::i:::i:i:i:i:iiiiiiii;iri;i;iri;iri;i;iririririririririr;;;i    //
//    i:ririiiiiiiiii:i:i:iiiiiiiiiii:i:i:i:iiiii:i:i:i::::::::::::::,:,,,,.,.....,.,.,,:,::::::::i:i:::i:i:iiiiiiiiii;iiiiiii;iriii;iriiiriririiiiiii;irir:    //
//    :::::::i:i:i:iiiiiiiiiiiiiii:i:i:iii:i::::::::::::::::::::,:,:,:,,.,...........,.,,::::::::::i:i:i:i:iiiiiiiiiiiiiiiiii;iiiiiii;i;iri;iriiiii;iiirirri    //
//    r:;ii:::iiiii:iii:iii:iiiiiii:i:iii::::::::::::::::,:::::,:,,,,......         ....,.,,:,::::::::::i:i:i:::i:i:i:i:i:i:i:iiiii:iiiiiiiiiiiiiiiiii;i;ir:    //
//    ;ir777riii:::::::i:i:iii:iii:i:i::::::::::::::::::::::::::::,:,,....             ....,.,.,,:,::::::::::::::::::::i:::i:i:iiiiiiiiiiiiiiiiiiiiii;iririi    //
//    i:iiiiriiiiiiii:::::::iii:i:i:i:i:i:::i:i:i:i:i:i::::::::::,:,,..                 . ....,.,,:,::::::::::::::::i:i:i:iii:i:iiiiiiiiiiiiiiiiiiiiiiii;ir:    //
//    i::::::iiii;irii:::::::::iiiiiiiii:i:i:i:i:i:i:i::::::::,:,,,,.,...                ......,,,,:,:,::::::::i:i:iii:iiiii:iii:i:iii:i:i:iiiii:i:i:i:i:ii:    //
//    i,:::::,:,:::::::::::::,:,,:i:i:i:::i:i:i:i:i::::::::::::::::,:.,..               ....::::::i:i:iii:iii:i:i:i:i:i:i:i:i:i:i:i:i:i:i:i:i:i:::i:i:iiii;:    //
//    ::::::::::::::::iiii:iii::,,.,,::::::::i::::::::,:::::,:,,,,....                 .,::::::::::::::::::::::::::::::::::::::::i:i:::i:i:iiiiiir;r;r;rrrri    //
//    uYS5XSXXPkNPPPPSqPqkX5kSX5S22uurrrrriii::,:,::ii:,:.,.,.,,,.........,.. .      .:::.::::::::::::::i:i:i:::::::::::::i:i:i:iiiiiiii;i;iriri;iri;iiirir:    //
//    S1SSkk1F5FYvvvrr77iri::;i::iiiiiii:::::::i:i:::::i:;;r;riiirr77vrririi:,.. ......::iii:::::::i:i:iiiiii;i;iiiiiiiiiiiiiiiiiiiiiiiiiiiiii:i:i:i:iiii;ii    //
//    rir;rii::i::::::i:::i:::::::::::::::i:::i:i:i:i:iiiiri;irii::::::::,..... ..:::::::iiiri;iiiiii:iiiiri;iri;i;iri;iriii;i;iiiiiiiii;iiiiiiiiiiiiiririr:    //
//    7rrrr;ii:i:::i:iii:ii;iii;iii;i;iiiii;i;iiiiiiii:i:ii;ii:i::,:,:,:::,,.,...,,..,:::::::i:i:i:::::i:iii:iiii;i;i;i;iriii;ir;r;riri;i;iririr;riririii;ii    //
//    i:iiiiiiii;i;i;i;iiiiiiir;ririr;r;rirrrrrrrirrr;ririi:iiriiiiiiii:i:i:i:i:i:iiiiiiiiiiii;i;i;iriiiiiii;i;;riririiiii;irir;r;r;r;rr7r7rrr7rr;rrrrrr7r7i    //
//    ;iiririr;rrrrr;r;rirrrrr;rrrrrrrr7rr;rrrrrr7r7rrrr;riririririri;i;irir;;i;iririrrrr7rrr7r7r77777r7r7rrrrr7r77LvY7Lvv7v777vrrr7r7r7r7vL777v7LLLLLLY7jYv    //
//    rirrr;rrrrrrrrrrrr7r7r7r7r7r7r777777v7v7v7v7v7v7v7v77rr;ri;i7rrr777r7r7rrrrirrrrrr7rr;777r7777777rv777v7vr77v7777r77v7Lvvv7vLvYJUjLYYLYvLLYYjYuYjLLLJ7    //
//    rrr7r7r7r7r7r7r777777v7v777v7v7777777777r7r7r7;rrrrririrrvv7iriri;ii:i:i:i:rrvrr;ri;irrrrrr7r7r777777LLLvv7v7ri7i;rv7rrvvv7YLjL777rv77rv7v777v7777r777    //
//    7i7rrr7r777r7rrr7rrr7r7r7777777vvrvvL7LLjvvLL7v7vLuLJj25PkqSuvLJuJL7LjuJuuuUk1uvjjUu1jY7vYvLLLYYuuUjuYuu1uuuUjUJuYuJujYLj7LLYYuujr7vvr7rr7LLv7vvYLYvUJ    //
//    j77v7Lvv777v7LLjLjLLvYvJuFUuYu2k2S1FuJuuuuYJJ2ujJJLYvLYJLjvv7LvuuUuF2JLYLjYv7i,:i77v77r7777L7L7v777v7777rr7uuYvLrvLj7vY7;7vjYuuULS1uJSY7uJ7vr7u1LuLYJj    //
//    Lrv7v7v777YYYvLLLLYL77v7Lrr;iii;7rriiir7ririri:ir::,::::i:,:::i:iiiii;vii;v77::,::rr;r7ir7vvv7vLuuu7vvu1u7r7uu1jvJjLUU2j1uuUkSF211S2uJY7Y7i:rUur72jrr:    //
//    L7777v77rrirrrii:ii;iii;ii:;i:::::ii::.......::::::ii::::::;7r:r7r::irvr:rviiiiiirrv77L7rLrrrii7r7rrrri7YYYJvLLvJu77jUv7LJvUvJuuL777rriir7r7rrirrLriii    //
//    1LJLuLLvYL7LuJjYJLvLvrv7vir7v7v7UjY;iiiii::iYu7i:iv7L7771FUvv7vrvvvrriiir777vvjLuSv::;v7r7:irri:::i:i7rii:i:iirrv77r77vvL7rrrr77v7v7777vuu2JL7vjri720O    //
//    vrvvvvLLLuu25P15FSjLYJvjrirr7vr77LYLrr7r;vi7i::i:7i:::i7rriri:::.,::iiir::,iiii77v77irii7LLLvuuvrrrr::::,::,:i::,,::,,,::i:iiiii:iir;r;7r7777LLuU21SFk    //
//    v;v77r7J77j7vvYLu7YvLvYvj77vLvvr777ru2LrUYY7rvrLLL2vv7UUUL7:ririri:7L:,.,ir.,::.:i:.:,i:,:iiii7;ri:::::,,,:,::::::::::i::,..,::::::::iii::i::ii::::::.    //
//    2JYYvLJjLY7rvLrLL7rv;7Jr7LvuJvuU7UX22X25NX111GZGF5ZG0PuYvFuuY7vX1JLL7jqJrYJr:rvrrLrrvv7i,ii::ri::i:i,.ir;:,:ii:i:::7rvLu77LLrvrr7vJJLJ7rirrriiirii::i;    //
//    Lr77vri:r7vvL7JLLr;iii7rY7v;7;rriii::,:iiiir7iri:;rir7Yiirr:i:ii, ,,::i:::i;i:rvvi7::::iirvii:::ii7iiirrr::::,:::,:ii:i:::ir7i:.:iii::::::77rrv7L7YLv2    //
//    PXP0XXFuuvjX51JuJvi;:ivvrirL7r,,,,,,:::,.,:ii;iiiii;iriii7r;i7rY777rii:::7rLii,,:i..,ir77rvv7vvv777YvrLLiUNFYkFu1Ujvirr:ii;uvvL7LuvuJY7i;7;irriri.:r7:    //
//    7irrr;rr7LkL1Jri7vjuv77;;iir77v7YvjUEESj1uYjkuLrii7r::iirri7LLvLjuSkqOOGBBB8EOOGGXuFk5jLLr77rr77r:riii7::r7rLjYU51E5LLY2MOE2qG07uYU5vjZMBqNPOZOZZu1Uvi    //
//    ;iirii::.ii:,i7JriiJ22SF22F12PNF1FSFvJ5Li;777v7uLr7iiriri7i;7rii:::i7rvF152uL2vUSGM@B@B@@BOBMO8EPPEOOOXPSuJuk7.i7i:,,,,;::.:rJiir27;rvkJirr7ruvu1rr;:i    //
//    qXOEGG0Xu55kEGMSkOEjY77ivL77vrLJLri7irY;riiiiir:;i7irr7::::..iv:,SMMr.:vY;riv1jr:,ivY7r77ir:::::rrUGqSUuXqZXZvrr7i:::i77;r7r::,,:,::7i,,v5rLvJiir;7rr7    //
//    i;vj7ii;:r77::::,rrvLuvL2ZZOZ88OOO8OEZZMMBMM08q0P00GZ8027v7FuO@@8@B@BB;7LrLFZPLr::..,::;Lri7irujj7rr:ii7J215r7FuPGEOOMZX522LiYvLYYYLuj7rLr:i::::irir;:    //
//    uvJ2S5qXUL1kujFX271F1u0Pk111SXOEPqPSPkqPq5F2kSGN8GNNk7i7Fk@B@B@B@@BM@BB.::i:i;7r1rrr1JrYj21ukOOMMGE2FNquLr7iLU7vFN008GZEOGOXj1Z8MOMOOGZNPuJvYuUJrir::i    //
//    MMMMMMOMOO8MMMOq0GXFu1552Fu7:jY77u25XNFXFF25XPk17iiri7jXEMB@MBM@MBMMM@i:r..i:ijjLkZE51XSFkqEX1vLYFSXuvLu7riiiirjFN2Fq0XZZO0G8O8MOO8OOMG8ZOGZqSEZOMOGOO    //
//    X2UJLvSqPSkF7rLLUU15Pq0PEPNXN2LjS5F1JL2US5S21Lri::7jOB@B@BBMBMMMBMBB@PiUqu5S7jYi7rv5u;7ii:;7F1vvjY2ir::;iir7rrjrYPGG02SqNXZE0Nk12LJ7Lu515151SFUv7,:LjJ    //
//    U225222SFS1Sr72qPkSkSkXOZ0NOZOZEPqk5u5Sk5kSqSSSN0M@@B@B@BBMBMBMBMBB@B@GMOMOOOOE8Zk1Ek1LYSULi:;777Lrr2F2ZGZqqEGPFLJi:iiir:7uJvLuuLL7UYL1ZGOZG0ZE05772uv    //
//    BOBM@MMM@MBMBBM88OMOM8O88OMMOOMOBGGGB80G@BO0qEBB@B@BBMBMBMBMBMBMBB@GqG8ZOOBB@B@B@B@B@B@B@MM08k2u2ju2OPXGM8Zk0Svi7:,:rv7i:,:,. :,.,ii:,rrv7vjkkEZZ880ES    //
//    ZZMMN00XuSJ7i7uk0UuuXGEqUu7L:::irukZ00NFvFXFNBB@BBMBMBMBMBMBB@BBM@BYLUU5u1Y77vLYvJr;:i7r::ii::,::rrr7;:iiFk2kY:rYuJLrv77u7:;J2u7;227i7ri:ri:::ivJ2rL77    //
//    i,rY5SSuu2qNSY0qNLr;1qq::iiLULi:, ..,.:i:,.v@@BMBMBMBMMMBMBM@B@B@B@ :iri:::,i::,. .  .:.iFr:;;u1Fui:rr::7riJEPLvEkkSZOBBMOBMBMMOM8OOGZZZMOMGZPXUSXFqOX    //
//    SuLUk0U8O8M@B@GqMMu7LkSu1SF2vu77PPUvvJjvi,u@BBMBMBMBMBMBM@B@@Ui@M@B. ,i7i,::ijuur7YuPGOOUjEM8O8OZZE8E8ZMOGXk1uJSkXkF1XSXkPNGE0NENGN00GZGG8GO8O8MOOGG8G    //
//    ZvUuUkGB@NP0q1vi77rirv2Uv7LYjPOO@Bq5G8U;jP@B@MBMBMBMBMBB@B@@@GS@@B@riuUivkZZuirirkMO8FYuP0Z0OqqkE0PFFXNqNPZ7::rkXPG0Xiiu0PXSFUS2uFPE8Z8E00Z0NPNqqXPPG0    //
//    7irYr:O5:rv,:i::::i7rii7:rii:,iJvuUFSqOM2XB@BBBBBBMBMBB@B0XOB@BBM@B@7LL;LPSkur7uirr:::ir:i..:LJUuFSPXqLuPqP22OE5;v5NFuUPNGZOEEEEqEPqG8Z80GGGEZE0NGEG0Z    //
//    Uru27u@:,:uU1uuFE2rvLvLu000NN2i,:..:UJJ: 2@B@MBM@MBBBB@GLr, :EBMBB@@@q@B@B@8MBOB@B@BBZGOMPFu10ONX5XXXXqu;irv2kXS0017uk2UUJJ7rvkPZENXkSPFF5kkPXPFkSXSX1    //
//                                                                                                                                                              //
//                                                                                                                                                              //
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////


contract imo is ERC721Creator {
    constructor() ERC721Creator("resolute2023", "imo") {}
}

// File: contracts/manifold/ERC721Creator.sol




// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

/// @author: manifold.xyz

import "@openzeppelin/contracts/proxy/Proxy.sol";
import "@openzeppelin/contracts/utils/Address.sol";
import "@openzeppelin/contracts/utils/StorageSlot.sol";

contract ERC721Creator is Proxy {
    
    constructor(string memory name, string memory symbol) {
        assert(_IMPLEMENTATION_SLOT == bytes32(uint256(keccak256("eip1967.proxy.implementation")) - 1));
        StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value = 0x2d3fC875de7Fe7Da43AD0afa0E7023c9B91D06b1;
        Address.functionDelegateCall(
            0x2d3fC875de7Fe7Da43AD0afa0E7023c9B91D06b1,
            abi.encodeWithSignature("initialize(string,string)", name, symbol)
        );
    }
        
    /**
     * @dev Storage slot with the address of the current implementation.
     * This is the keccak-256 hash of "eip1967.proxy.implementation" subtracted by 1, and is
     * validated in the constructor.
     */
    bytes32 internal constant _IMPLEMENTATION_SLOT = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc;

    /**
     * @dev Returns the current implementation address.
     */
     function implementation() public view returns (address) {
        return _implementation();
    }

    function _implementation() internal override view returns (address) {
        return StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value;
    }    

}

// File: node_modules/@openzeppelin/contracts/proxy/Proxy.sol



// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.6.0) (proxy/Proxy.sol)

pragma solidity ^0.8.0;

/**
 * @dev This abstract contract provides a fallback function that delegates all calls to another contract using the EVM
 * instruction `delegatecall`. We refer to the second contract as the _implementation_ behind the proxy, and it has to
 * be specified by overriding the virtual {_implementation} function.
 *
 * Additionally, delegation to the implementation can be triggered manually through the {_fallback} function, or to a
 * different contract through the {_delegate} function.
 *
 * The success and return data of the delegated call will be returned back to the caller of the proxy.
 */
abstract contract Proxy {
    /**
     * @dev Delegates the current call to `implementation`.
     *
     * This function does not return to its internal call site, it will return directly to the external caller.
     */
    function _delegate(address implementation) internal virtual {
        assembly {
            // Copy msg.data. We take full control of memory in this inline assembly
            // block because it will not return to Solidity code. We overwrite the
            // Solidity scratch pad at memory position 0.
            calldatacopy(0, 0, calldatasize())

            // Call the implementation.
            // out and outsize are 0 because we don't know the size yet.
            let result := delegatecall(gas(), implementation, 0, calldatasize(), 0, 0)

            // Copy the returned data.
            returndatacopy(0, 0, returndatasize())

            switch result
            // delegatecall returns 0 on error.
            case 0 {
                revert(0, returndatasize())
            }
            default {
                return(0, returndatasize())
            }
        }
    }

    /**
     * @dev This is a virtual function that should be overridden so it returns the address to which the fallback function
     * and {_fallback} should delegate.
     */
    function _implementation() internal view virtual returns (address);

    /**
     * @dev Delegates the current call to the address returned by `_implementation()`.
     *
     * This function does not return to its internal call site, it will return directly to the external caller.
     */
    function _fallback() internal virtual {
        _beforeFallback();
        _delegate(_implementation());
    }

    /**
     * @dev Fallback function that delegates calls to the address returned by `_implementation()`. Will run if no other
     * function in the contract matches the call data.
     */
    fallback() external payable virtual {
        _fallback();
    }

    /**
     * @dev Fallback function that delegates calls to the address returned by `_implementation()`. Will run if call data
     * is empty.
     */
    receive() external payable virtual {
        _fallback();
    }

    /**
     * @dev Hook that is called before falling back to the implementation. Can happen as part of a manual `_fallback`
     * call, or as part of the Solidity `fallback` or `receive` functions.
     *
     * If overridden should call `super._beforeFallback()`.
     */
    function _beforeFallback() internal virtual {}
}

// File: node_modules/@openzeppelin/contracts/utils/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: node_modules/@openzeppelin/contracts/utils/StorageSlot.sol



// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.7.0) (utils/StorageSlot.sol)

pragma solidity ^0.8.0;

/**
 * @dev Library for reading and writing primitive types to specific storage slots.
 *
 * Storage slots are often used to avoid storage conflict when dealing with upgradeable contracts.
 * This library helps with reading and writing to such slots without the need for inline assembly.
 *
 * The functions in this library return Slot structs that contain a `value` member that can be used to read or write.
 *
 * Example usage to set ERC1967 implementation slot:
 * ```
 * contract ERC1967 {
 *     bytes32 internal constant _IMPLEMENTATION_SLOT = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc;
 *
 *     function _getImplementation() internal view returns (address) {
 *         return StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value;
 *     }
 *
 *     function _setImplementation(address newImplementation) internal {
 *         require(Address.isContract(newImplementation), "ERC1967: new implementation is not a contract");
 *         StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value = newImplementation;
 *     }
 * }
 * ```
 *
 * _Available since v4.1 for `address`, `bool`, `bytes32`, and `uint256`._
 */
library StorageSlot {
    struct AddressSlot {
        address value;
    }

    struct BooleanSlot {
        bool value;
    }

    struct Bytes32Slot {
        bytes32 value;
    }

    struct Uint256Slot {
        uint256 value;
    }

    /**
     * @dev Returns an `AddressSlot` with member `value` located at `slot`.
     */
    function getAddressSlot(bytes32 slot) internal pure returns (AddressSlot storage r) {
        /// @solidity memory-safe-assembly
        assembly {
            r.slot := slot
        }
    }

    /**
     * @dev Returns an `BooleanSlot` with member `value` located at `slot`.
     */
    function getBooleanSlot(bytes32 slot) internal pure returns (BooleanSlot storage r) {
        /// @solidity memory-safe-assembly
        assembly {
            r.slot := slot
        }
    }

    /**
     * @dev Returns an `Bytes32Slot` with member `value` located at `slot`.
     */
    function getBytes32Slot(bytes32 slot) internal pure returns (Bytes32Slot storage r) {
        /// @solidity memory-safe-assembly
        assembly {
            r.slot := slot
        }
    }

    /**
     * @dev Returns an `Uint256Slot` with member `value` located at `slot`.
     */
    function getUint256Slot(bytes32 slot) internal pure returns (Uint256Slot storage r) {
        /// @solidity memory-safe-assembly
        assembly {
            r.slot := slot
        }
    }
}