ETH Price: $3,319.34 (-5.67%)

Contract

0x947804256C9c46967cC55bBBBF6C0E93923AFf2C
 

Overview

ETH Balance

0 ETH

Eth Value

$0.00

Multichain Info

No addresses found
Transaction Hash
Method
Block
From
To
Change Admin197584242024-04-29 3:55:59211 days ago1714362959IN
0x94780425...3923AFf2C
0 ETH0.000135034.72174863
Change Admin197584242024-04-29 3:55:59211 days ago1714362959IN
0x94780425...3923AFf2C
0 ETH0.000135034.72174863
Deploy195881422024-04-05 7:45:59235 days ago1712303159IN
0x94780425...3923AFf2C
0 ETH0.0023443318.58355449
Deploy195881412024-04-05 7:45:47235 days ago1712303147IN
0x94780425...3923AFf2C
0 ETH0.0023977219.00675084
0x60808060195881402024-04-05 7:45:35235 days ago1712303135IN
 Create: ERC1967Factory
0 ETH0.0116152519.265903

Latest 2 internal transactions

Advanced mode:
Parent Transaction Hash Block From To
195881422024-04-05 7:45:59235 days ago1712303159
0x94780425...3923AFf2C
 Contract Creation0 ETH
195881412024-04-05 7:45:47235 days ago1712303147
0x94780425...3923AFf2C
 Contract Creation0 ETH
Loading...
Loading

Contract Source Code Verified (Exact Match)

Contract Name:
ERC1967Factory

Compiler Version
v0.8.25+commit.b61c2a91

Optimization Enabled:
Yes with 20000 runs

Other Settings:
paris EvmVersion
File 1 of 1 : ERC1967Factory.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

/// @notice Factory for deploying and managing ERC1967 proxy contracts.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/ERC1967Factory.sol)
/// @author jtriley-eth (https://github.com/jtriley-eth/minimum-viable-proxy)
contract ERC1967Factory {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                       CUSTOM ERRORS                        */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

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

    /// @dev The proxy deployment failed.
    error DeploymentFailed();

    /// @dev The upgrade failed.
    error UpgradeFailed();

    /// @dev The salt does not start with the caller.
    error SaltDoesNotStartWithCaller();

    /// @dev `bytes4(keccak256(bytes("Unauthorized()")))`.
    uint256 internal constant _UNAUTHORIZED_ERROR_SELECTOR = 0x82b42900;

    /// @dev `bytes4(keccak256(bytes("DeploymentFailed()")))`.
    uint256 internal constant _DEPLOYMENT_FAILED_ERROR_SELECTOR = 0x30116425;

    /// @dev `bytes4(keccak256(bytes("UpgradeFailed()")))`.
    uint256 internal constant _UPGRADE_FAILED_ERROR_SELECTOR = 0x55299b49;

    /// @dev `bytes4(keccak256(bytes("SaltDoesNotStartWithCaller()")))`.
    uint256 internal constant _SALT_DOES_NOT_START_WITH_CALLER_ERROR_SELECTOR = 0x2f634836;

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

    /// @dev The admin of a proxy contract has been changed.
    event AdminChanged(address indexed proxy, address indexed admin);

    /// @dev The implementation for a proxy has been upgraded.
    event Upgraded(address indexed proxy, address indexed implementation);

    /// @dev A proxy has been deployed.
    event Deployed(address indexed proxy, address indexed implementation, address indexed admin);

    /// @dev `keccak256(bytes("AdminChanged(address,address)"))`.
    uint256 internal constant _ADMIN_CHANGED_EVENT_SIGNATURE =
        0x7e644d79422f17c01e4894b5f4f588d331ebfa28653d42ae832dc59e38c9798f;

    /// @dev `keccak256(bytes("Upgraded(address,address)"))`.
    uint256 internal constant _UPGRADED_EVENT_SIGNATURE =
        0x5d611f318680d00598bb735d61bacf0c514c6b50e1e5ad30040a4df2b12791c7;

    /// @dev `keccak256(bytes("Deployed(address,address,address)"))`.
    uint256 internal constant _DEPLOYED_EVENT_SIGNATURE =
        0xc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082;

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

    // The admin slot for a `proxy` is `shl(96, proxy)`.

    /// @dev The ERC-1967 storage slot for the implementation in the proxy.
    /// `uint256(keccak256("eip1967.proxy.implementation")) - 1`.
    uint256 internal constant _IMPLEMENTATION_SLOT =
        0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc;

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

    /// @dev Returns the admin of the proxy.
    function adminOf(address proxy) public view returns (address admin) {
        assembly {
            admin := sload(shl(96, proxy))
        }
    }

    /// @dev Sets the admin of the proxy.
    /// The caller of this function must be the admin of the proxy on this factory.
    function changeAdmin(address proxy, address admin) public {
        assembly {
            // Check if the caller is the admin of the proxy.
            if iszero(eq(sload(shl(96, proxy)), caller())) {
                mstore(0x00, _UNAUTHORIZED_ERROR_SELECTOR)
                revert(0x1c, 0x04)
            }
            // Store the admin for the proxy.
            sstore(shl(96, proxy), admin)
            // Emit the {AdminChanged} event.
            log3(0, 0, _ADMIN_CHANGED_EVENT_SIGNATURE, proxy, admin)
        }
    }

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

    /// @dev Upgrades the proxy to point to `implementation`.
    /// The caller of this function must be the admin of the proxy on this factory.
    function upgrade(address proxy, address implementation) public payable {
        upgradeAndCall(proxy, implementation, _emptyData());
    }

    /// @dev Upgrades the proxy to point to `implementation`.
    /// Then, calls the proxy with abi encoded `data`.
    /// The caller of this function must be the admin of the proxy on this factory.
    function upgradeAndCall(address proxy, address implementation, bytes calldata data)
        public
        payable
    {
        assembly {
            // Check if the caller is the admin of the proxy.
            if iszero(eq(sload(shl(96, proxy)), caller())) {
                mstore(0x00, _UNAUTHORIZED_ERROR_SELECTOR)
                revert(0x1c, 0x04)
            }
            // Set up the calldata to upgrade the proxy.
            let m := mload(0x40)
            mstore(m, implementation)
            mstore(add(m, 0x20), _IMPLEMENTATION_SLOT)
            calldatacopy(add(m, 0x40), data.offset, data.length)
            // Try upgrading the proxy and revert upon failure.
            if iszero(call(gas(), proxy, callvalue(), m, add(0x40, data.length), 0x00, 0x00)) {
                // Revert with the `UpgradeFailed` selector if there is no error returndata.
                if iszero(returndatasize()) {
                    mstore(0x00, _UPGRADE_FAILED_ERROR_SELECTOR)
                    revert(0x1c, 0x04)
                }
                // Otherwise, bubble up the returned error.
                returndatacopy(0x00, 0x00, returndatasize())
                revert(0x00, returndatasize())
            }
            // Emit the {Upgraded} event.
            log3(0, 0, _UPGRADED_EVENT_SIGNATURE, proxy, implementation)
        }
    }

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

    /// @dev Deploys a proxy for `implementation`, with `admin`,
    /// and returns its address.
    /// The value passed into this function will be forwarded to the proxy.
    function deploy(address implementation, address admin) public payable returns (address proxy) {
        proxy = deployAndCall(implementation, admin, _emptyData());
    }

    /// @dev Deploys a proxy for `implementation`, with `admin`,
    /// and returns its address.
    /// The value passed into this function will be forwarded to the proxy.
    /// Then, calls the proxy with abi encoded `data`.
    function deployAndCall(address implementation, address admin, bytes calldata data)
        public
        payable
        returns (address proxy)
    {
        proxy = _deploy(implementation, admin, bytes32(0), false, data);
    }

    /// @dev Deploys a proxy for `implementation`, with `admin`, `salt`,
    /// and returns its deterministic address.
    /// The value passed into this function will be forwarded to the proxy.
    function deployDeterministic(address implementation, address admin, bytes32 salt)
        public
        payable
        returns (address proxy)
    {
        proxy = deployDeterministicAndCall(implementation, admin, salt, _emptyData());
    }

    /// @dev Deploys a proxy for `implementation`, with `admin`, `salt`,
    /// and returns its deterministic address.
    /// The value passed into this function will be forwarded to the proxy.
    /// Then, calls the proxy with abi encoded `data`.
    function deployDeterministicAndCall(
        address implementation,
        address admin,
        bytes32 salt,
        bytes calldata data
    ) public payable returns (address proxy) {
        assembly {
            // If the salt does not start with the zero address or the caller.
            if iszero(or(iszero(shr(96, salt)), eq(caller(), shr(96, salt)))) {
                mstore(0x00, _SALT_DOES_NOT_START_WITH_CALLER_ERROR_SELECTOR)
                revert(0x1c, 0x04)
            }
        }
        proxy = _deploy(implementation, admin, salt, true, data);
    }

    /// @dev Deploys the proxy, with optionality to deploy deterministically with a `salt`.
    function _deploy(
        address implementation,
        address admin,
        bytes32 salt,
        bool useSalt,
        bytes calldata data
    ) internal returns (address proxy) {
        bytes32 m = _initCode();
        assembly {
            // Create the proxy.
            switch useSalt
            case 0 { proxy := create(0, add(m, 0x13), 0x88) }
            default { proxy := create2(0, add(m, 0x13), 0x88, salt) }
            // Revert if the creation fails.
            if iszero(proxy) {
                mstore(0x00, _DEPLOYMENT_FAILED_ERROR_SELECTOR)
                revert(0x1c, 0x04)
            }

            // Set up the calldata to set the implementation of the proxy.
            mstore(m, implementation)
            mstore(add(m, 0x20), _IMPLEMENTATION_SLOT)
            calldatacopy(add(m, 0x40), data.offset, data.length)
            // Try setting the implementation on the proxy and revert upon failure.
            if iszero(call(gas(), proxy, callvalue(), m, add(0x40, data.length), 0x00, 0x00)) {
                // Revert with the `DeploymentFailed` selector if there is no error returndata.
                if iszero(returndatasize()) {
                    mstore(0x00, _DEPLOYMENT_FAILED_ERROR_SELECTOR)
                    revert(0x1c, 0x04)
                }
                // Otherwise, bubble up the returned error.
                returndatacopy(0x00, 0x00, returndatasize())
                revert(0x00, returndatasize())
            }

            // Store the admin for the proxy.
            sstore(shl(96, proxy), admin)

            // Emit the {Deployed} event.
            log4(0, 0, _DEPLOYED_EVENT_SIGNATURE, proxy, implementation, admin)
        }
    }

    /// @dev Returns the address of the proxy deployed with `salt`.
    function predictDeterministicAddress(bytes32 salt) public view returns (address predicted) {
        bytes32 hash = initCodeHash();
        assembly {
            // Compute and store the bytecode hash.
            mstore8(0x00, 0xff) // Write the prefix.
            mstore(0x35, hash)
            mstore(0x01, shl(96, address()))
            mstore(0x15, salt)
            // Note: `predicted` has dirty upper 96 bits. We won't clean it here
            // as it will be automatically cleaned when it is copied into the returndata.
            // Please clean as needed if used in other inline assembly blocks.
            predicted := keccak256(0x00, 0x55)
            // Restore the part of the free memory pointer that has been overwritten.
            mstore(0x35, 0)
        }
    }

    /// @dev Returns the initialization code hash of the proxy.
    /// Used for mining vanity addresses with create2crunch.
    function initCodeHash() public view returns (bytes32 result) {
        bytes32 m = _initCode();
        assembly {
            result := keccak256(add(m, 0x13), 0x88)
        }
    }

    /// @dev Returns a pointer to the initialization code of a proxy created via this factory.
    function _initCode() internal view returns (bytes32 m) {
        assembly {
            /**
             * -------------------------------------------------------------------------------------+
             * CREATION (9 bytes)                                                                   |
             * -------------------------------------------------------------------------------------|
             * Opcode     | Mnemonic        | Stack               | Memory                          |
             * -------------------------------------------------------------------------------------|
             * 60 runSize | PUSH1 runSize   | r                   |                                 |
             * 3d         | RETURNDATASIZE  | 0 r                 |                                 |
             * 81         | DUP2            | r 0 r               |                                 |
             * 60 offset  | PUSH1 offset    | o r 0 r             |                                 |
             * 3d         | RETURNDATASIZE  | 0 o r 0 r           |                                 |
             * 39         | CODECOPY        | 0 r                 | [0..runSize): runtime code      |
             * f3         | RETURN          |                     | [0..runSize): runtime code      |
             * -------------------------------------------------------------------------------------|
             * RUNTIME (127 bytes)                                                                  |
             * -------------------------------------------------------------------------------------|
             * Opcode      | Mnemonic       | Stack               | Memory                          |
             * -------------------------------------------------------------------------------------|
             *                                                                                      |
             * ::: keep some values in stack :::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | 0                   |                                 |
             * 3d          | RETURNDATASIZE | 0 0                 |                                 |
             *                                                                                      |
             * ::: check if caller is factory ::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 33          | CALLER         | c 0 0               |                                 |
             * 73 factory  | PUSH20 factory | f c 0 0             |                                 |
             * 14          | EQ             | isf 0 0             |                                 |
             * 60 0x57     | PUSH1 0x57     | dest isf 0 0        |                                 |
             * 57          | JUMPI          | 0 0                 |                                 |
             *                                                                                      |
             * ::: copy calldata to memory :::::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 36          | CALLDATASIZE   | cds 0 0             |                                 |
             * 3d          | RETURNDATASIZE | 0 cds 0 0           |                                 |
             * 3d          | RETURNDATASIZE | 0 0 cds 0 0         |                                 |
             * 37          | CALLDATACOPY   | 0 0                 | [0..calldatasize): calldata     |
             *                                                                                      |
             * ::: delegatecall to implementation ::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 36          | CALLDATASIZE   | cds 0 0             | [0..calldatasize): calldata     |
             * 3d          | RETURNDATASIZE | 0 cds 0 0           | [0..calldatasize): calldata     |
             * 7f slot     | PUSH32 slot    | s 0 cds 0 0         | [0..calldatasize): calldata     |
             * 54          | SLOAD          | i 0 cds 0 0         | [0..calldatasize): calldata     |
             * 5a          | GAS            | g i 0 cds 0 0       | [0..calldatasize): calldata     |
             * f4          | DELEGATECALL   | succ                | [0..calldatasize): calldata     |
             *                                                                                      |
             * ::: copy returndata to memory :::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | rds succ            | [0..calldatasize): calldata     |
             * 60 0x00     | PUSH1 0x00     | 0 rds succ          | [0..calldatasize): calldata     |
             * 80          | DUP1           | 0 0 rds succ        | [0..calldatasize): calldata     |
             * 3e          | RETURNDATACOPY | succ                | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: branch on delegatecall status :::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 60 0x52     | PUSH1 0x52     | dest succ           | [0..returndatasize): returndata |
             * 57          | JUMPI          |                     | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: delegatecall failed, revert :::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | rds                 | [0..returndatasize): returndata |
             * 60 0x00     | PUSH1 0x00     | 0 rds               | [0..returndatasize): returndata |
             * fd          | REVERT         |                     | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: delegatecall succeeded, return ::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 5b          | JUMPDEST       |                     | [0..returndatasize): returndata |
             * 3d          | RETURNDATASIZE | rds                 | [0..returndatasize): returndata |
             * 60 0x00     | PUSH1 0x00     | 0 rds               | [0..returndatasize): returndata |
             * f3          | RETURN         |                     | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: set new implementation (caller is factory) ::::::::::::::::::::::::::::::::::::: |
             * 5b          | JUMPDEST       | 0 0                 |                                 |
             * 3d          | RETURNDATASIZE | 0 0 0               |                                 |
             * 35          | CALLDATALOAD   | impl 0 0            |                                 |
             * 60 0x20     | PUSH1 0x20     | w impl 0 0          |                                 |
             * 35          | CALLDATALOAD   | slot impl 0 0       |                                 |
             * 55          | SSTORE         | 0 0                 |                                 |
             *                                                                                      |
             * ::: no extra calldata, return :::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 60 0x40     | PUSH1 0x40     | 2w 0 0              |                                 |
             * 80          | DUP1           | 2w 2w 0 0           |                                 |
             * 36          | CALLDATASIZE   | cds 2w 2w 0 0       |                                 |
             * 11          | GT             | gt 2w 0 0           |                                 |
             * 15          | ISZERO         | lte 2w 0 0          |                                 |
             * 60 0x52     | PUSH1 0x52     | dest lte 2w 0 0     |                                 |
             * 57          | JUMPI          | 2w 0 0              |                                 |
             *                                                                                      |
             * ::: copy extra calldata to memory :::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 36          | CALLDATASIZE   | cds 2w 0 0          |                                 |
             * 03          | SUB            | t 0 0               |                                 |
             * 80          | DUP1           | t t 0 0             |                                 |
             * 60 0x40     | PUSH1 0x40     | 2w t t 0 0          |                                 |
             * 3d          | RETURNDATASIZE | 0 2w t t 0 0        |                                 |
             * 37          | CALLDATACOPY   | t 0 0               | [0..t): extra calldata          |
             *                                                                                      |
             * ::: delegatecall to implementation ::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | 0 t 0 0             | [0..t): extra calldata          |
             * 3d          | RETURNDATASIZE | 0 0 t 0 0           | [0..t): extra calldata          |
             * 35          | CALLDATALOAD   | i 0 t 0 0           | [0..t): extra calldata          |
             * 5a          | GAS            | g i 0 t 0 0         | [0..t): extra calldata          |
             * f4          | DELEGATECALL   | succ                | [0..t): extra calldata          |
             *                                                                                      |
             * ::: copy returndata to memory :::::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | rds succ            | [0..t): extra calldata          |
             * 60 0x00     | PUSH1 0x00     | 0 rds succ          | [0..t): extra calldata          |
             * 80          | DUP1           | 0 0 rds succ        | [0..t): extra calldata          |
             * 3e          | RETURNDATACOPY | succ                | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: branch on delegatecall status :::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 60 0x52     | PUSH1 0x52     | dest succ           | [0..returndatasize): returndata |
             * 57          | JUMPI          |                     | [0..returndatasize): returndata |
             *                                                                                      |
             * ::: delegatecall failed, revert :::::::::::::::::::::::::::::::::::::::::::::::::::: |
             * 3d          | RETURNDATASIZE | rds                 | [0..returndatasize): returndata |
             * 60 0x00     | PUSH1 0x00     | 0 rds               | [0..returndatasize): returndata |
             * fd          | REVERT         |                     | [0..returndatasize): returndata |
             * -------------------------------------------------------------------------------------+
             */
            m := mload(0x40)
            // forgefmt: disable-start
            switch shr(112, address())
            case 0 {
                // If the factory's address has six or more leading zero bytes.
                mstore(add(m, 0x75), 0x604c573d6000fd) // 7
                mstore(add(m, 0x6e), 0x3d3560203555604080361115604c5736038060403d373d3d355af43d6000803e) // 32
                mstore(add(m, 0x4e), 0x3735a920a3ca505d382bbc545af43d6000803e604c573d6000fd5b3d6000f35b) // 32
                mstore(add(m, 0x2e), 0x14605157363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc) // 32
                mstore(add(m, 0x0e), address()) // 14
                mstore(m, 0x60793d8160093d39f33d3d336d) // 9 + 4
            }
            default {
                mstore(add(m, 0x7b), 0x6052573d6000fd) // 7
                mstore(add(m, 0x74), 0x3d356020355560408036111560525736038060403d373d3d355af43d6000803e) // 32
                mstore(add(m, 0x54), 0x3735a920a3ca505d382bbc545af43d6000803e6052573d6000fd5b3d6000f35b) // 32
                mstore(add(m, 0x34), 0x14605757363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc) // 32
                mstore(add(m, 0x14), address()) // 20
                mstore(m, 0x607f3d8160093d39f33d3d3373) // 9 + 4
            }
            // forgefmt: disable-end
        }
    }

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

    /// @dev Helper function to return an empty bytes calldata.
    function _emptyData() internal pure returns (bytes calldata data) {
        assembly {
            data.length := 0
        }
    }
}

Settings
{
  "remappings": [
    "@openzeppelin/=node_modules/@openzeppelin/",
    "@openzeppelin-upgradeable/=node_modules/@openzeppelin/contracts-upgradeable/",
    "solady/=node_modules/solady/",
    "forge-std/=lib/forge-std/src/"
  ],
  "optimizer": {
    "enabled": true,
    "runs": 20000
  },
  "metadata": {
    "useLiteralContent": false,
    "bytecodeHash": "ipfs",
    "appendCBOR": true
  },
  "outputSelection": {
    "*": {
      "*": [
        "evm.bytecode",
        "evm.deployedBytecode",
        "devdoc",
        "userdoc",
        "metadata",
        "abi"
      ]
    }
  },
  "evmVersion": "paris",
  "viaIR": true,
  "libraries": {}
}

Contract Security Audit

Contract ABI

[{"inputs":[],"name":"DeploymentFailed","type":"error"},{"inputs":[],"name":"SaltDoesNotStartWithCaller","type":"error"},{"inputs":[],"name":"Unauthorized","type":"error"},{"inputs":[],"name":"UpgradeFailed","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"proxy","type":"address"},{"indexed":true,"internalType":"address","name":"admin","type":"address"}],"name":"AdminChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"proxy","type":"address"},{"indexed":true,"internalType":"address","name":"implementation","type":"address"},{"indexed":true,"internalType":"address","name":"admin","type":"address"}],"name":"Deployed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"proxy","type":"address"},{"indexed":true,"internalType":"address","name":"implementation","type":"address"}],"name":"Upgraded","type":"event"},{"inputs":[{"internalType":"address","name":"proxy","type":"address"}],"name":"adminOf","outputs":[{"internalType":"address","name":"admin","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"proxy","type":"address"},{"internalType":"address","name":"admin","type":"address"}],"name":"changeAdmin","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"implementation","type":"address"},{"internalType":"address","name":"admin","type":"address"}],"name":"deploy","outputs":[{"internalType":"address","name":"proxy","type":"address"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"implementation","type":"address"},{"internalType":"address","name":"admin","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"deployAndCall","outputs":[{"internalType":"address","name":"proxy","type":"address"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"implementation","type":"address"},{"internalType":"address","name":"admin","type":"address"},{"internalType":"bytes32","name":"salt","type":"bytes32"}],"name":"deployDeterministic","outputs":[{"internalType":"address","name":"proxy","type":"address"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"implementation","type":"address"},{"internalType":"address","name":"admin","type":"address"},{"internalType":"bytes32","name":"salt","type":"bytes32"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"deployDeterministicAndCall","outputs":[{"internalType":"address","name":"proxy","type":"address"}],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"initCodeHash","outputs":[{"internalType":"bytes32","name":"result","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"salt","type":"bytes32"}],"name":"predictDeterministicAddress","outputs":[{"internalType":"address","name":"predicted","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"proxy","type":"address"},{"internalType":"address","name":"implementation","type":"address"}],"name":"upgrade","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"proxy","type":"address"},{"internalType":"address","name":"implementation","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"upgradeAndCall","outputs":[],"stateMutability":"payable","type":"function"}]

608080604052346015576109ef908161001b8239f35b600080fdfe6080604052600436101561001257600080fd5b6000803560e01c9081631acfd02a146100ba575080632abbef15146100b55780633729f922146100b05780634314f120146100ab5780635414dff0146100a6578063545e7c61146100a15780639623609d1461009c57806399a88ec414610097578063a97b90d5146100925763db4c545e1461008d57600080fd5b610837565b61071e565b610675565b6105c7565b6104f0565b610474565b6103b3565b6101e6565b61018b565b3461013d5760407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261013d576100f1610140565b6100f9610168565b908060601b33815403610130578290557f7e644d79422f17c01e4894b5f4f588d331ebfa28653d42ae832dc59e38c9798f8380a380f35b6382b4290084526004601cfd5b80fd5b6004359073ffffffffffffffffffffffffffffffffffffffff8216820361016357565b600080fd5b6024359073ffffffffffffffffffffffffffffffffffffffff8216820361016357565b346101635760207ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc3601126101635760206101c4610140565b60601b5473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b60607ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610218610140565b610220610168565b90604435918260601c803314901517156102fa5761023c61087e565b9160009360886013850186f59283156102ed5784604082848394527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015234875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b833d156102e0573d81803e3d90fd5b633011642590526004601cfd5b633011642585526004601cfd5b632f6348366000526004601cfd5b9181601f840112156101635782359167ffffffffffffffff8311610163576020838186019501011161016357565b60607ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc8201126101635773ffffffffffffffffffffffffffffffffffffffff9160043583811681036101635792602435908116810361016357916044359067ffffffffffffffff8211610163576103af91600401610308565b9091565b6103bc36610336565b926103c892919261087e565b60009460886013830187f094851561046757918187939284938684527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602085015260408401376040019034875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b633011642587526004601cfd5b346101635760207ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357608860136104af61087e565b012060ff6000536035523060601b60015260043560155260206055600020600060355273ffffffffffffffffffffffffffffffffffffffff60405191168152f35b60407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610522610140565b61052a610168565b61053261087e565b9060009260886013840185f09283156102ed5784604082848394527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015234875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b6105d036610336565b929092338260601b54036106675780604051948486527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602087015260408601376000809481926040019034855af11561064b577f5d611f318680d00598bb735d61bacf0c514c6b50e1e5ad30040a4df2b12791c78380a380f35b823d1561065a573d81803e3d90fd5b6355299b4990526004601cfd5b6382b429006000526004601cfd5b60407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc360112610163576106a7610140565b6106af610168565b338260601b54036106675760409182518281527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015260008094819234855af11561064b577f5d611f318680d00598bb735d61bacf0c514c6b50e1e5ad30040a4df2b12791c78380a380f35b60807ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610750610140565b610758610168565b906044359160643567ffffffffffffffff81116101635761077d903690600401610308565b8460609492941c803314901517156102fa5761079761087e565b9060009560886013840188f594851561046757918187939284938684527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602085015260408401376040019034875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b346101635760007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc3601126101635760206088601361087461087e565b0120604051908152f35b604051903060701c1561092257666052573d6000fd607b8301527f3d356020355560408036111560525736038060403d373d3d355af43d6000803e60748301527f3735a920a3ca505d382bbc545af43d6000803e6052573d6000fd5b3d6000f35b60548301527f14605757363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc60348301523060148301526c607f3d8160093d39f33d3d33738252565b66604c573d6000fd60758301527f3d3560203555604080361115604c5736038060403d373d3d355af43d6000803e606e8301527f3735a920a3ca505d382bbc545af43d6000803e604c573d6000fd5b3d6000f35b604e8301527f14605157363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc602e83015230600e8301526c60793d8160093d39f33d3d336d825256fea2646970667358221220df9b0b2fc7d01cc45a642dddf155c34eb6e126067f50fd4b64b458757c414c5064736f6c63430008190033

Deployed Bytecode

0x6080604052600436101561001257600080fd5b6000803560e01c9081631acfd02a146100ba575080632abbef15146100b55780633729f922146100b05780634314f120146100ab5780635414dff0146100a6578063545e7c61146100a15780639623609d1461009c57806399a88ec414610097578063a97b90d5146100925763db4c545e1461008d57600080fd5b610837565b61071e565b610675565b6105c7565b6104f0565b610474565b6103b3565b6101e6565b61018b565b3461013d5760407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261013d576100f1610140565b6100f9610168565b908060601b33815403610130578290557f7e644d79422f17c01e4894b5f4f588d331ebfa28653d42ae832dc59e38c9798f8380a380f35b6382b4290084526004601cfd5b80fd5b6004359073ffffffffffffffffffffffffffffffffffffffff8216820361016357565b600080fd5b6024359073ffffffffffffffffffffffffffffffffffffffff8216820361016357565b346101635760207ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc3601126101635760206101c4610140565b60601b5473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b60607ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610218610140565b610220610168565b90604435918260601c803314901517156102fa5761023c61087e565b9160009360886013850186f59283156102ed5784604082848394527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015234875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b833d156102e0573d81803e3d90fd5b633011642590526004601cfd5b633011642585526004601cfd5b632f6348366000526004601cfd5b9181601f840112156101635782359167ffffffffffffffff8311610163576020838186019501011161016357565b60607ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc8201126101635773ffffffffffffffffffffffffffffffffffffffff9160043583811681036101635792602435908116810361016357916044359067ffffffffffffffff8211610163576103af91600401610308565b9091565b6103bc36610336565b926103c892919261087e565b60009460886013830187f094851561046757918187939284938684527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602085015260408401376040019034875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b633011642587526004601cfd5b346101635760207ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357608860136104af61087e565b012060ff6000536035523060601b60015260043560155260206055600020600060355273ffffffffffffffffffffffffffffffffffffffff60405191168152f35b60407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610522610140565b61052a610168565b61053261087e565b9060009260886013840185f09283156102ed5784604082848394527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015234875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b6105d036610336565b929092338260601b54036106675780604051948486527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602087015260408601376000809481926040019034855af11561064b577f5d611f318680d00598bb735d61bacf0c514c6b50e1e5ad30040a4df2b12791c78380a380f35b823d1561065a573d81803e3d90fd5b6355299b4990526004601cfd5b6382b429006000526004601cfd5b60407ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc360112610163576106a7610140565b6106af610168565b338260601b54036106675760409182518281527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602082015260008094819234855af11561064b577f5d611f318680d00598bb735d61bacf0c514c6b50e1e5ad30040a4df2b12791c78380a380f35b60807ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc36011261016357610750610140565b610758610168565b906044359160643567ffffffffffffffff81116101635761077d903690600401610308565b8460609492941c803314901517156102fa5761079761087e565b9060009560886013840188f594851561046757918187939284938684527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc602085015260408401376040019034875af1156102d157827fc95935a66d15e0da5e412aca0ad27ae891d20b2fb91cf3994b6a3bf2b8178082602095848360601b5580a473ffffffffffffffffffffffffffffffffffffffff60405191168152f35b346101635760007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc3601126101635760206088601361087461087e565b0120604051908152f35b604051903060701c1561092257666052573d6000fd607b8301527f3d356020355560408036111560525736038060403d373d3d355af43d6000803e60748301527f3735a920a3ca505d382bbc545af43d6000803e6052573d6000fd5b3d6000f35b60548301527f14605757363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc60348301523060148301526c607f3d8160093d39f33d3d33738252565b66604c573d6000fd60758301527f3d3560203555604080361115604c5736038060403d373d3d355af43d6000803e606e8301527f3735a920a3ca505d382bbc545af43d6000803e604c573d6000fd5b3d6000f35b604e8301527f14605157363d3d37363d7f360894a13ba1a3210667c828492db98dca3e2076cc602e83015230600e8301526c60793d8160093d39f33d3d336d825256fea2646970667358221220df9b0b2fc7d01cc45a642dddf155c34eb6e126067f50fd4b64b458757c414c5064736f6c63430008190033

Block Transaction Difficulty Gas Used Reward
View All Blocks Produced

Block Uncle Number Difficulty Gas Used Reward
View All Uncles
Loading...
Loading
Loading...
Loading

Validator Index Block Amount
View All Withdrawals

Transaction Hash Block Value Eth2 PubKey Valid
View All Deposits
Loading...
Loading
[ Download: CSV Export  ]
[ Download: CSV Export  ]

A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.