Solidity – Pre-initialize a Variable Using EIP 1167 for Each Clone: Feasibility Analysis

eip-1167erc-721solidity

Question in short

Is it possible to pre-initialize a variable using EIP 1167 if the initial value is the same for each clone?

Why I want to do this?

I created an ERC721 contract that requires a user to hold another NFT to mint (membership) there are 4096 membership NFTs. In order to make minting cheaper, I have a uint256[180] variable where each value is pre-initialized at MAX_INT. At mint I update this array so I can set the tokenId at the position of the membershipId (the pre-initializing saves the end-user some gas at a cost for me).

Using EIP 1167 I can clone the contract, but not set the variable (which will always the same value initially).

Current implementation

Right now I set the variable in my initialize function, but this means it comes at a gas cost for me each time I clone a contract.

Initialize function

 uint256[180] public memberShipFlags;

 function initProject() public initializer {
      _setMembershipFlags();
 }

 function _setMembershipFlags() private {
        for (uint256 i = 0; i < 180; i++) {
            memberShipFlags[
                i
            ] = 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff;
         }
  }

Clone function

 function clone(address implementation) internal returns (address instance) {
        assembly {
            let ptr := mload(0x40)
            mstore(
                ptr,
                0x3d602d80600a3d3981f3363d3d373d3d3d363d73000000000000000000000000
            )
            mstore(add(ptr, 0x14), shl(0x60, implementation))
            mstore(
                add(ptr, 0x28),
                0x5af43d82803e903d91602b57fd5bf30000000000000000000000000000000000
            )
            instance := create(0, ptr, 0x37)
        }
        require(instance != address(0), "ERC1167: create failed");
 }

Question

Is there a better way to do this (considering it's always initialized at the exact same value)? I was hoping there might be a way to do this using assembly to change the bytecode.

Best Answer

No it is not possible to pre-initialize values with EIP-1167.

But if you use zero to represent that value then yes it is initialized as zero. If that storage location needs to be able to represent a logical value of zero then find some other value to represent zero.

Related Topic