Overview
ETH Balance
0 ETH
Eth Value
$0.00More Info
Private Name Tags
ContractCreator
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Loading...
Loading
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 Name:
CRFTDStakingToken
Compiler Version
v0.8.15+commit.e14f2714
Optimization Enabled:
Yes with 100000 runs
Other Settings:
default evmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {utils} from "./utils/utils.sol"; import {ERC721} from "solmate/tokens/ERC721.sol"; import {ERC20UDS} from "UDS/tokens/ERC20UDS.sol"; import {OwnableUDS} from "UDS/auth/OwnableUDS.sol"; import {UUPSUpgrade} from "UDS/proxy/UUPSUpgrade.sol"; import {ERC20RewardUDS} from "UDS/tokens/ERC20RewardUDS.sol"; // ------------- storage bytes32 constant DIAMOND_STORAGE_CRFTD_TOKEN = keccak256("diamond.storage.crftd.token"); function s() pure returns (CRFTDTokenDS storage diamondStorage) { bytes32 slot = DIAMOND_STORAGE_CRFTD_TOKEN; assembly { diamondStorage.slot := slot } // prettier-ignore } struct CRFTDTokenDS { uint256 rewardEndDate; mapping(address => uint256) rewardRate; mapping(address => mapping(uint256 => address)) ownerOf; } // ------------- errors error ZeroReward(); error IncorrectOwner(); error CollectionNotRegistered(); error CollectionAlreadyRegistered(); // ___ ___ ___ _____ // / /\ / /\ / /\ ___ / /::\ // / /:/ / /::\ / /:/_ /__/\ / /:/\:\ // / /:/ / /:/\:\ / /:/ /\ \ \:\ / /:/ \:\ // / /:/ ___ / /::\ \:\ / /:/ /:/ \__\:\ /__/:/ \__\:| // /__/:/ / /\ /__/:/\:\_\:\ /__/:/ /:/ / /::\ \ \:\ / /:/ // \ \:\ / /:/ \__\/~|::\/:/ \ \:\/:/ / /:/\:\ \ \:\ /:/ // \ \:\ /:/ | |:|::/ \ \::/ / /:/__\/ \ \:\/:/ // \ \:\/:/ | |:|\/ \ \:\ /__/:/ \ \::/ // \ \::/ |__|:| \ \:\ \__\/ \__\/ // \__\/ \__\| \__\/ /// @title CRFTDStakingToken /// @author phaze (https://github.com/0xPhaze) /// @notice Minimal ERC721 staking contract supporting multiple collections /// @notice Combines ERC20 Token to avoid external calls contract CRFTDStakingToken is ERC20RewardUDS, UUPSUpgrade, OwnableUDS { event CollectionRegistered(address indexed collection, uint256 rewardRate); /* ------------- init ------------- */ function init(string calldata name, string calldata symbol) external initializer { __Ownable_init(); __ERC20_init(name, symbol, 18); } /* ------------- public ------------- */ function rewardEndDate() public view override returns (uint256) { return s().rewardEndDate; } function rewardDailyRate() public pure override returns (uint256) { return 1e16; // 0.01 } function rewardRate(address collection) public view returns (uint256) { return s().rewardRate[collection]; } function ownerOf(address collection, uint256 id) public view returns (address) { return s().ownerOf[collection][id]; } function getDailyReward(address user) public view returns (uint256) { return _getRewardMultiplier(user) * rewardDailyRate(); } /* ------------- erc20 ------------- */ function transfer(address to, uint256 amount) public virtual override returns (bool) { _claimReward(msg.sender); return ERC20UDS.transfer(to, amount); } function transferFrom( address from, address to, uint256 amount ) public virtual override returns (bool) { _claimReward(from); return ERC20UDS.transferFrom(from, to, amount); } /* ------------- external ------------- */ function stake(address collection, uint256[] calldata tokenIds) external { uint256 rate = s().rewardRate[collection]; if (rate == 0) revert CollectionNotRegistered(); _increaseRewardMultiplier(msg.sender, uint216(tokenIds.length * rate)); for (uint256 i; i < tokenIds.length; ++i) { ERC721(collection).transferFrom(msg.sender, address(this), tokenIds[i]); s().ownerOf[collection][tokenIds[i]] = msg.sender; } } function unstake(address collection, uint256[] calldata tokenIds) external { uint256 rate = s().rewardRate[collection]; if (rate == 0) revert CollectionNotRegistered(); _decreaseRewardMultiplier(msg.sender, uint216(tokenIds.length * rate)); for (uint256 i; i < tokenIds.length; ++i) { if (s().ownerOf[collection][tokenIds[i]] != msg.sender) revert IncorrectOwner(); delete s().ownerOf[collection][tokenIds[i]]; ERC721(collection).transferFrom(address(this), msg.sender, tokenIds[i]); } } function claimReward() external { _claimReward(msg.sender); } /* ------------- O(n) read-only ------------- */ function stakedIdsOf( address collection, address user, uint256 collectionSize ) external view returns (uint256[] memory stakedIds) { return utils.getOwnedIds(s().ownerOf[collection], user, collectionSize); } /* ------------- owner ------------- */ function registerCollection(address collection, uint200 rate) external onlyOwner { if (rate == 0) revert ZeroReward(); if (s().rewardRate[collection] != 0) revert CollectionAlreadyRegistered(); s().rewardRate[collection] = rate; emit CollectionRegistered(collection, rate); } function setRewardEndDate(uint256 endDate) external onlyOwner { s().rewardEndDate = endDate; } function airdrop(address[] calldata tos, uint256[] calldata amounts) external onlyOwner { for (uint256 i; i < tos.length; ++i) _mint(tos[i], amounts[i]); } /* ------------- UUPSUpgrade ------------- */ function _authorizeUpgrade() internal override onlyOwner {} }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; library utils { function getOwnedIds( mapping(uint256 => address) storage ownerOf, address user, uint256 collectionSize ) internal view returns (uint256[] memory ids) { uint256 memPtr; uint256 idsLength; assembly { ids := mload(0x40) memPtr := add(ids, 32) } unchecked { uint256 end = collectionSize + 1; for (uint256 id = 0; id < end; ++id) { if (ownerOf[id] == user) { assembly { mstore(memPtr, id) memPtr := add(memPtr, 32) idsLength := add(idsLength, 1) } } } } assembly { mstore(ids, idsLength) mstore(0x40, memPtr) } } function indexOf(address[] calldata arr, address addr) internal pure returns (bool found, uint256 index) { unchecked { for (uint256 i; i < arr.length; ++i) if (arr[i] == addr) return (true, i); } return (false, 0); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.8.0; /// @notice Modern, minimalist, and gas efficient ERC-721 implementation. /// @author Solmate (https://github.com/Rari-Capital/solmate/blob/main/src/tokens/ERC721.sol) abstract contract ERC721 { /*////////////////////////////////////////////////////////////// EVENTS //////////////////////////////////////////////////////////////*/ event Transfer(address indexed from, address indexed to, uint256 indexed id); event Approval(address indexed owner, address indexed spender, uint256 indexed id); event ApprovalForAll(address indexed owner, address indexed operator, bool approved); /*////////////////////////////////////////////////////////////// METADATA STORAGE/LOGIC //////////////////////////////////////////////////////////////*/ string public name; string public symbol; function tokenURI(uint256 id) public view virtual returns (string memory); /*////////////////////////////////////////////////////////////// ERC721 BALANCE/OWNER STORAGE //////////////////////////////////////////////////////////////*/ mapping(uint256 => address) internal _ownerOf; mapping(address => uint256) internal _balanceOf; function ownerOf(uint256 id) public view virtual returns (address owner) { require((owner = _ownerOf[id]) != address(0), "NOT_MINTED"); } function balanceOf(address owner) public view virtual returns (uint256) { require(owner != address(0), "ZERO_ADDRESS"); return _balanceOf[owner]; } /*////////////////////////////////////////////////////////////// ERC721 APPROVAL STORAGE //////////////////////////////////////////////////////////////*/ mapping(uint256 => address) public getApproved; mapping(address => mapping(address => bool)) public isApprovedForAll; /*////////////////////////////////////////////////////////////// CONSTRUCTOR //////////////////////////////////////////////////////////////*/ constructor(string memory _name, string memory _symbol) { name = _name; symbol = _symbol; } /*////////////////////////////////////////////////////////////// ERC721 LOGIC //////////////////////////////////////////////////////////////*/ function approve(address spender, uint256 id) public virtual { address owner = _ownerOf[id]; require(msg.sender == owner || isApprovedForAll[owner][msg.sender], "NOT_AUTHORIZED"); getApproved[id] = spender; emit Approval(owner, spender, id); } function setApprovalForAll(address operator, bool approved) public virtual { isApprovedForAll[msg.sender][operator] = approved; emit ApprovalForAll(msg.sender, operator, approved); } function transferFrom( address from, address to, uint256 id ) public virtual { require(from == _ownerOf[id], "WRONG_FROM"); require(to != address(0), "INVALID_RECIPIENT"); require( msg.sender == from || isApprovedForAll[from][msg.sender] || msg.sender == getApproved[id], "NOT_AUTHORIZED" ); // Underflow of the sender's balance is impossible because we check for // ownership above and the recipient's balance can't realistically overflow. unchecked { _balanceOf[from]--; _balanceOf[to]++; } _ownerOf[id] = to; delete getApproved[id]; emit Transfer(from, to, id); } function safeTransferFrom( address from, address to, uint256 id ) public virtual { transferFrom(from, to, id); if (to.code.length != 0) require( ERC721TokenReceiver(to).onERC721Received(msg.sender, from, id, "") == ERC721TokenReceiver.onERC721Received.selector, "UNSAFE_RECIPIENT" ); } function safeTransferFrom( address from, address to, uint256 id, bytes calldata data ) public virtual { transferFrom(from, to, id); if (to.code.length != 0) require( ERC721TokenReceiver(to).onERC721Received(msg.sender, from, id, data) == ERC721TokenReceiver.onERC721Received.selector, "UNSAFE_RECIPIENT" ); } /*////////////////////////////////////////////////////////////// ERC165 LOGIC //////////////////////////////////////////////////////////////*/ function supportsInterface(bytes4 interfaceId) public view virtual returns (bool) { return interfaceId == 0x01ffc9a7 || // ERC165 Interface ID for ERC165 interfaceId == 0x80ac58cd || // ERC165 Interface ID for ERC721 interfaceId == 0x5b5e139f; // ERC165 Interface ID for ERC721Metadata } /*////////////////////////////////////////////////////////////// INTERNAL MINT/BURN LOGIC //////////////////////////////////////////////////////////////*/ function _mint(address to, uint256 id) internal virtual { require(to != address(0), "INVALID_RECIPIENT"); require(_ownerOf[id] == address(0), "ALREADY_MINTED"); // Counter overflow is incredibly unrealistic. unchecked { _balanceOf[to]++; } _ownerOf[id] = to; emit Transfer(address(0), to, id); } function _burn(uint256 id) internal virtual { address owner = _ownerOf[id]; require(owner != address(0), "NOT_MINTED"); // Ownership check above ensures no underflow. unchecked { _balanceOf[owner]--; } delete _ownerOf[id]; delete getApproved[id]; emit Transfer(owner, address(0), id); } /*////////////////////////////////////////////////////////////// INTERNAL SAFE MINT LOGIC //////////////////////////////////////////////////////////////*/ function _safeMint(address to, uint256 id) internal virtual { _mint(to, id); if (to.code.length != 0) require( ERC721TokenReceiver(to).onERC721Received(msg.sender, address(0), id, "") == ERC721TokenReceiver.onERC721Received.selector, "UNSAFE_RECIPIENT" ); } function _safeMint( address to, uint256 id, bytes memory data ) internal virtual { _mint(to, id); if (to.code.length != 0) require( ERC721TokenReceiver(to).onERC721Received(msg.sender, address(0), id, data) == ERC721TokenReceiver.onERC721Received.selector, "UNSAFE_RECIPIENT" ); } } /// @notice A generic interface for a contract which properly accepts ERC721 tokens. /// @author Solmate (https://github.com/Rari-Capital/solmate/blob/main/src/tokens/ERC721.sol) abstract contract ERC721TokenReceiver { function onERC721Received( address, address, uint256, bytes calldata ) external virtual returns (bytes4) { return ERC721TokenReceiver.onERC721Received.selector; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {Initializable} from "../auth/Initializable.sol"; import {EIP712PermitUDS} from "../auth/EIP712PermitUDS.sol"; // ------------- storage bytes32 constant DIAMOND_STORAGE_ERC20 = keccak256("diamond.storage.erc20"); function s() pure returns (ERC20DS storage diamondStorage) { bytes32 slot = DIAMOND_STORAGE_ERC20; assembly { diamondStorage.slot := slot } // prettier-ignore } struct ERC20DS { string name; string symbol; uint8 decimals; uint256 totalSupply; mapping(address => uint256) balanceOf; mapping(address => mapping(address => uint256)) allowance; } /// @title ERC20 (Upgradeable Diamond Storage) /// @author phaze (https://github.com/0xPhaze/UDS) /// @author Modified from Solmate (https://github.com/Rari-Capital/solmate) abstract contract ERC20UDS is Initializable, EIP712PermitUDS { event Transfer(address indexed from, address indexed to, uint256 amount); event Approval(address indexed owner, address indexed operator, uint256 amount); /* ------------- init ------------- */ function __ERC20_init( string memory _name, string memory _symbol, uint8 _decimals ) internal initializer { s().name = _name; s().symbol = _symbol; s().decimals = _decimals; } /* ------------- view ------------- */ function name() external view virtual returns (string memory) { return s().name; } function symbol() external view virtual returns (string memory) { return s().symbol; } function decimals() external view virtual returns (uint8) { return s().decimals; } function totalSupply() external view virtual returns (uint256) { return s().totalSupply; } function balanceOf(address owner) public view virtual returns (uint256) { return s().balanceOf[owner]; } function allowance(address owner, address operator) public view virtual returns (uint256) { return s().allowance[owner][operator]; } /* ------------- public ------------- */ function approve(address operator, uint256 amount) public virtual returns (bool) { s().allowance[msg.sender][operator] = amount; emit Approval(msg.sender, operator, amount); return true; } function transfer(address to, uint256 amount) public virtual returns (bool) { s().balanceOf[msg.sender] -= amount; unchecked { s().balanceOf[to] += amount; } emit Transfer(msg.sender, to, amount); return true; } function transferFrom( address from, address to, uint256 amount ) public virtual returns (bool) { uint256 allowed = s().allowance[from][msg.sender]; if (allowed != type(uint256).max) s().allowance[from][msg.sender] = allowed - amount; s().balanceOf[from] -= amount; unchecked { s().balanceOf[to] += amount; } emit Transfer(from, to, amount); return true; } // EIP-2612 permit function permit( address owner, address operator, uint256 value, uint256 deadline, uint8 v, bytes32 r, bytes32 s_ ) public virtual { if (_usePermit(owner, operator, value, deadline, v, r, s_)) { s().allowance[owner][operator] = value; emit Approval(owner, operator, value); } } /* ------------- internal ------------- */ function _mint(address to, uint256 amount) internal virtual { s().totalSupply += amount; unchecked { s().balanceOf[to] += amount; } emit Transfer(address(0), to, amount); } function _burn(address from, uint256 amount) internal virtual { s().balanceOf[from] -= amount; unchecked { s().totalSupply -= amount; } emit Transfer(from, address(0), amount); } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {Initializable} from "./Initializable.sol"; // ------------- storage bytes32 constant DIAMOND_STORAGE_OWNABLE = keccak256("diamond.storage.ownable"); function s() pure returns (OwnableDS storage diamondStorage) { bytes32 slot = DIAMOND_STORAGE_OWNABLE; assembly { diamondStorage.slot := slot } // prettier-ignore } struct OwnableDS { address owner; } // ------------- errors error CallerNotOwner(); /// @title Ownable (Upgradeable Diamond Storage) /// @author phaze (https://github.com/0xPhaze/UDS) /// @dev Requires `__Ownable_init` to be called in proxy abstract contract OwnableUDS is Initializable { event OwnerChanged(address oldOwner, address newOwner); function __Ownable_init() internal initializer { s().owner = msg.sender; } /* ------------- external ------------- */ function owner() public view returns (address) { return s().owner; } function transferOwnership(address newOwner) external onlyOwner { s().owner = newOwner; emit OwnerChanged(msg.sender, newOwner); } /* ------------- modifier ------------- */ modifier onlyOwner() { if (msg.sender != s().owner) revert CallerNotOwner(); _; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {ERC1967, ERC1967_PROXY_STORAGE_SLOT} from "./ERC1967Proxy.sol"; // ------------- errors error OnlyProxyCallAllowed(); error DelegateCallNotAllowed(); /// @notice Minimal UUPSUpgrade /// @author phaze (https://github.com/0xPhaze/UDS) abstract contract UUPSUpgrade is ERC1967 { address private immutable __implementation = address(this); /* ------------- external ------------- */ function upgradeToAndCall(address logic, bytes calldata data) external { _authorizeUpgrade(); _upgradeToAndCall(logic, data); } /* ------------- view ------------- */ function proxiableUUID() external view virtual notDelegated returns (bytes32) { return ERC1967_PROXY_STORAGE_SLOT; } /* ------------- virtual ------------- */ function _authorizeUpgrade() internal virtual; /* ------------- modifier ------------- */ modifier onlyProxy() { if (address(this) == __implementation) revert OnlyProxyCallAllowed(); _; } modifier notDelegated() { if (address(this) != __implementation) revert DelegateCallNotAllowed(); _; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {ERC20UDS, s as erc20ds} from "./ERC20UDS.sol"; // ------------- storage bytes32 constant DIAMOND_STORAGE_ERC20_REWARD = keccak256("diamond.storage.erc20.reward"); function s() pure returns (ERC20RewardDS storage diamondStorage) { bytes32 slot = DIAMOND_STORAGE_ERC20_REWARD; assembly { diamondStorage.slot := slot } // prettier-ignore } struct UserData { uint216 multiplier; uint40 lastClaimed; } struct ERC20RewardDS { mapping(address => UserData) userData; } /// @title ERC20Reward (Upgradeable Diamond Storage) /// @author phaze (https://github.com/0xPhaze/UDS) /// @notice Allows for ERC20 reward accrual /// @notice at a rate of rewardDailyRate() * multiplier[user] per day /// @notice Tokens are automatically claimed before any multiplier update abstract contract ERC20RewardUDS is ERC20UDS { /* ------------- virtual ------------- */ function rewardEndDate() public view virtual returns (uint256); function rewardDailyRate() public view virtual returns (uint256); /* ------------- view ------------- */ function totalBalanceOf(address owner) public view virtual returns (uint256) { return ERC20UDS.balanceOf(owner) + pendingReward(owner); } function pendingReward(address owner) public view virtual returns (uint256) { UserData storage userData = s().userData[owner]; return _calculateReward(userData.multiplier, userData.lastClaimed); } /* ------------- internal ------------- */ function _getRewardMultiplier(address owner) internal view virtual returns (uint256) { return s().userData[owner].multiplier; } function _calculateReward(uint256 multiplier, uint256 lastClaimed) internal view virtual returns (uint256) { uint256 end = rewardEndDate(); uint256 timestamp = block.timestamp; if (lastClaimed > end) return 0; else if (timestamp > end) timestamp = end; // if multiplier > 0 then lastClaimed > 0 // because _claimReward must have been called return ((timestamp - lastClaimed) * multiplier * rewardDailyRate()) / 1 days; } function _claimReward(address owner) internal virtual { UserData storage userData = s().userData[owner]; uint256 multiplier = userData.multiplier; uint256 lastClaimed = userData.lastClaimed; if (multiplier != 0 || lastClaimed == 0) { // only forego minting if multiplier == 0 // checking for amount == 0 can lead to failed transactions // due to too little gas being supplied through estimation if (multiplier != 0) { uint256 amount = _calculateReward(multiplier, lastClaimed); _mint(owner, amount); } s().userData[owner].lastClaimed = uint40(block.timestamp); } } function _increaseRewardMultiplier(address owner, uint216 quantity) internal virtual { _claimReward(owner); s().userData[owner].multiplier += quantity; } function _decreaseRewardMultiplier(address owner, uint216 quantity) internal virtual { _claimReward(owner); s().userData[owner].multiplier -= quantity; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; import {s as erc1967ds} from "../proxy/ERC1967Proxy.sol"; // ------------- errors error ProxyCallRequired(); error AlreadyInitialized(); /// @title Initializable /// @author phaze (https://github.com/0xPhaze/UDS) /// @dev functions using the `initializer` modifier are only callable during proxy deployment /// @dev functions using the `reinitializer` modifier are only callable through a proxy /// @dev and only before a proxy upgrade migration has completed /// @dev (only when `upgradeToAndCall`'s `initCalldata` is being executed) /// @dev allows re-initialization during upgrades abstract contract Initializable { address private immutable __implementation = address(this); /* ------------- modifier ------------- */ modifier initializer() { if (address(this).code.length != 0) revert AlreadyInitialized(); _; } modifier reinitializer() { if (address(this) == __implementation) revert ProxyCallRequired(); if (erc1967ds().implementation == __implementation) revert AlreadyInitialized(); _; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; // ------------- storage bytes32 constant DIAMOND_STORAGE_EIP_712_PERMIT = keccak256("diamond.storage.eip.712.permit"); function s() pure returns (EIP2612DS storage diamondStorage) { bytes32 slot = DIAMOND_STORAGE_EIP_712_PERMIT; assembly { diamondStorage.slot := slot } // prettier-ignore } struct EIP2612DS { mapping(address => uint256) nonces; } // ------------- errors error InvalidSigner(); error DeadlineExpired(); /// @title EIP712Permit (Upgradeable Diamond Storage) /// @author phaze (https://github.com/0xPhaze/UDS) /// @author Modified from Solmate (https://github.com/Rari-Capital/solmate) /// @dev `DOMAIN_SEPARATOR` needs to be re-computed every time /// @dev for use with a proxy due to `address(this)` abstract contract EIP712PermitUDS { /* ------------- public ------------- */ function nonces(address owner) public view returns (uint256) { return s().nonces[owner]; } function DOMAIN_SEPARATOR() public view virtual returns (bytes32) { return keccak256( abi.encode( keccak256("EIP712Domain(string name,string version,uint256 chainId,address verifyingContract)"), keccak256("EIP712"), keccak256("1"), block.chainid, address(this) ) ); } /* ------------- internal ------------- */ function _usePermit( address owner, address spender, uint256 value, uint256 deadline, uint8 v_, bytes32 r_, bytes32 s_ ) internal virtual returns (bool) { if (deadline < block.timestamp) revert DeadlineExpired(); unchecked { uint256 nonce = s().nonces[owner]++; address recovered = ecrecover( keccak256( abi.encodePacked( "\x19\x01", DOMAIN_SEPARATOR(), keccak256( abi.encode( keccak256( "Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)" ), owner, spender, value, nonce, deadline ) ) ) ), v_, r_, s_ ); if (recovered == address(0) || recovered != owner) revert InvalidSigner(); } return true; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; // ------------- storage // keccak256("eip1967.proxy.implementation") - 1 = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc; bytes32 constant ERC1967_PROXY_STORAGE_SLOT = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc; function s() pure returns (ERC1967UpgradeDS storage diamondStorage) { assembly { diamondStorage.slot := ERC1967_PROXY_STORAGE_SLOT } // prettier-ignore } struct ERC1967UpgradeDS { address implementation; } // ------------- errors error InvalidUUID(); error NotAContract(); /// @notice ERC1967 /// @author phaze (https://github.com/0xPhaze/UDS) abstract contract ERC1967 { event Upgraded(address indexed implementation); function _upgradeToAndCall(address logic, bytes memory data) internal { if (logic.code.length == 0) revert NotAContract(); if (ERC1822(logic).proxiableUUID() != ERC1967_PROXY_STORAGE_SLOT) revert InvalidUUID(); if (data.length != 0) { (bool success, ) = logic.delegatecall(data); if (!success) { assembly { returndatacopy(0, 0, returndatasize()) revert(0, returndatasize()) } } } emit Upgraded(logic); s().implementation = logic; } } /// @notice Minimal ERC1967Proxy /// @author phaze (https://github.com/0xPhaze/UDS) contract ERC1967Proxy is ERC1967 { constructor(address logic, bytes memory data) payable { _upgradeToAndCall(logic, data); } fallback() external payable { assembly { calldatacopy(0, 0, calldatasize()) let success := delegatecall(gas(), sload(ERC1967_PROXY_STORAGE_SLOT), 0, calldatasize(), 0, 0) returndatacopy(0, 0, returndatasize()) if success { return(0, returndatasize()) } revert(0, returndatasize()) } } } /// @notice ERC1822 /// @author phaze (https://github.com/0xPhaze/UDS) abstract contract ERC1822 { function proxiableUUID() external view virtual returns (bytes32); }
{ "remappings": [ "ArrayUtils/=lib/ArrayUtils/src/", "CRFTD/=src/", "UDS/=lib/UDS/src/", "ds-test/=lib/solmate/lib/ds-test/src/", "f-utils/=lib/f-utils/src/", "forge-std/=lib/forge-std/src/", "script/=script/", "solmate/=lib/solmate/src/", "src/=src/", "test/=test/", "src/=src/", "test/=test/", "script/=script/" ], "optimizer": { "enabled": true, "runs": 100000 }, "metadata": { "bytecodeHash": "ipfs" }, "outputSelection": { "*": { "*": [ "evm.bytecode", "evm.deployedBytecode", "devdoc", "userdoc", "metadata", "abi" ] } }, "evmVersion": "london", "libraries": {} }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
[{"inputs":[],"name":"AlreadyInitialized","type":"error"},{"inputs":[],"name":"CallerNotOwner","type":"error"},{"inputs":[],"name":"CollectionAlreadyRegistered","type":"error"},{"inputs":[],"name":"CollectionNotRegistered","type":"error"},{"inputs":[],"name":"DeadlineExpired","type":"error"},{"inputs":[],"name":"DelegateCallNotAllowed","type":"error"},{"inputs":[],"name":"IncorrectOwner","type":"error"},{"inputs":[],"name":"InvalidSigner","type":"error"},{"inputs":[],"name":"InvalidUUID","type":"error"},{"inputs":[],"name":"NotAContract","type":"error"},{"inputs":[],"name":"ZeroReward","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"collection","type":"address"},{"indexed":false,"internalType":"uint256","name":"rewardRate","type":"uint256"}],"name":"CollectionRegistered","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"oldOwner","type":"address"},{"indexed":false,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnerChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"implementation","type":"address"}],"name":"Upgraded","type":"event"},{"inputs":[],"name":"DOMAIN_SEPARATOR","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"tos","type":"address[]"},{"internalType":"uint256[]","name":"amounts","type":"uint256[]"}],"name":"airdrop","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"allowance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"approve","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"claimReward","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"decimals","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"user","type":"address"}],"name":"getDailyReward","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"name","type":"string"},{"internalType":"string","name":"symbol","type":"string"}],"name":"init","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"nonces","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"},{"internalType":"uint256","name":"id","type":"uint256"}],"name":"ownerOf","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"pendingReward","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint8","name":"v","type":"uint8"},{"internalType":"bytes32","name":"r","type":"bytes32"},{"internalType":"bytes32","name":"s_","type":"bytes32"}],"name":"permit","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"proxiableUUID","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"},{"internalType":"uint200","name":"rate","type":"uint200"}],"name":"registerCollection","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"rewardDailyRate","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"pure","type":"function"},{"inputs":[],"name":"rewardEndDate","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"}],"name":"rewardRate","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"endDate","type":"uint256"}],"name":"setRewardEndDate","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"},{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"}],"name":"stake","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"},{"internalType":"address","name":"user","type":"address"},{"internalType":"uint256","name":"collectionSize","type":"uint256"}],"name":"stakedIdsOf","outputs":[{"internalType":"uint256[]","name":"stakedIds","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"totalBalanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transfer","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transferFrom","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"collection","type":"address"},{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"}],"name":"unstake","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"logic","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"upgradeToAndCall","outputs":[],"stateMutability":"nonpayable","type":"function"}]
Contract Creation Code
60c060405230608081905260a05234801561001957600080fd5b5060805160a051612c6461003c6000396000610971015260005050612c646000f3fe608060405234801561001057600080fd5b50600436106101e55760003560e01c8063672434821161010f578063b88a802f116100a2578063dd62ed3e11610071578063dd62ed3e1461062d578063e4ab593d14610692578063f2fde38b146106b2578063f40f0f52146106c557600080fd5b8063b88a802f146105ec578063c5b41b89146105f4578063c9a3911e14610607578063d505accf1461061a57600080fd5b80637ecebe00116100de5780637ecebe001461053f5780638da5cb5b1461059457806395d89b41146105d1578063a9059cbb146105d957600080fd5b806367243482146104b15780637029144c146104c457806370a08231146104d75780637abdab561461052c57600080fd5b8063313ce567116101875780634f1ef286116101565780634f1ef2861461045a57806352d1902d1461046f5780635dbe4756146104775780635f36e2521461048a57600080fd5b8063313ce567146103585780633644e5151461038c5780633d9e7719146104345780634b0ee02a1461044757600080fd5b806318160ddd116101c357806318160ddd146102425780631f29d2dc14610269578063221ca18c146102f057806323b872dd1461034557600080fd5b806306fdde03146101ea578063095ea7b31461020857806316336c651461022b575b600080fd5b6101f26106d8565b6040516101ff9190612411565b60405180910390f35b61021b61021636600461248b565b610789565b60405190151581526020016101ff565b662386f26fc100005b6040519081526020016101ff565b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dba54610234565b6102cb61027736600461248b565b73ffffffffffffffffffffffffffffffffffffffff91821660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee6020908152604080832093835292905220541690565b60405173ffffffffffffffffffffffffffffffffffffffff90911681526020016101ff565b6102346102fe3660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604090205490565b61021b6103533660046124d0565b61081e565b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db95460405160ff90911681526020016101ff565b610234604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f60208201527f421979463954f2ac93264f1ce0c11a780b4a7686122abe11bac8c8244f44a3de918101919091527fc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc660608201524660808201523060a082015260009060c00160405160208183030381529060405280519060200120905090565b6102346104423660046124b5565b61083c565b6102346104553660046124b5565b6108b0565b61046d610468366004612555565b61090a565b005b610234610957565b61046d6104853660046125ed565b6109ed565b7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec54610234565b61046d6104bf366004612633565b610cbb565b61046d6104d236600461269f565b610d8e565b6102346104e53660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb602052604090205490565b61046d61053a3660046126ff565b610e4b565b61023461054d3660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f24034dbc71162a0a127c76a8ce123f10641be888cbac564cd2e6e6f5e2c19b81602052604090205490565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff166102cb565b6101f2611029565b61021b6105e736600461248b565b61105a565b61046d611076565b61046d610602366004612754565b611081565b61046d6106153660046125ed565b611115565b61046d61062836600461276d565b61133e565b61023461063b3660046127e0565b73ffffffffffffffffffffffffffffffffffffffff91821660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc6020908152604080832093909416825291909152205490565b6106a56106a03660046124d0565b6113e5565b6040516101ff9190612813565b61046d6106c03660046124b5565b611437565b6102346106d33660046124b5565b611545565b60607f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7805461070690612857565b80601f016020809104026020016040519081016040528092919081815260200182805461073290612857565b801561077f5780601f106107545761010080835404028352916020019161077f565b820191906000526020600020905b81548152906001019060200180831161076257829003601f168201915b5050505050905090565b3360008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc6020908152604080832073ffffffffffffffffffffffffffffffffffffffff871680855290835281842086905590518581529293909290917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591015b60405180910390a35060015b92915050565b6000610829846115d9565b610834848484611725565b949350505050565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081205461081890662386f26fc10000907affffffffffffffffffffffffffffffffffffffffffffffffffffff166128d9565b60006108bb82611545565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60205260409020546108189190612916565b6109126118df565b6109528383838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061194f92505050565b505050565b60003073ffffffffffffffffffffffffffffffffffffffff7f000000000000000000000000000000000000000000000000000000000000000016146109c8576040517f0d89438e00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc90565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604081205490819003610a6c576040517fa973256400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610a7f33610a7a83856128d9565b611b95565b60005b82811015610cb45773ffffffffffffffffffffffffffffffffffffffff851660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee602052604081203391868685818110610ae257610ae261292e565b602090810292909201358352508101919091526040016000205473ffffffffffffffffffffffffffffffffffffffff1614610b49576040517f3a6bbed300000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff851660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee6020526040812090858584818110610ba057610ba061292e565b6020908102929092013583525081019190915260400160002080547fffffffffffffffffffffffff000000000000000000000000000000000000000016905573ffffffffffffffffffffffffffffffffffffffff85166323b872dd3033878786818110610c0f57610c0f61292e565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e088901b16815273ffffffffffffffffffffffffffffffffffffffff958616600482015294909316602485015250602090910201356044820152606401600060405180830381600087803b158015610c8b57600080fd5b505af1158015610c9f573d6000803e3d6000fd5b5050505080610cad9061295d565b9050610a82565b5050505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff163314610d2b576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b60005b83811015610cb457610d7e858583818110610d4b57610d4b61292e565b9050602002016020810190610d6091906124b5565b848484818110610d7257610d7261292e565b90506020020135611c5f565b610d878161295d565b9050610d2e565b303b15610dc7576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610dcf611d18565b610e4584848080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8801819004810282018101909252868152925086915085908190840183828082843760009201919091525060129250611d9c915050565b50505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff163314610ebb576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8078ffffffffffffffffffffffffffffffffffffffffffffffffff16600003610f10576040517f9c1b278400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff821660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604090205415610f8c576040517f41ab882d00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff821660008181527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602090815260409182902078ffffffffffffffffffffffffffffffffffffffffffffffffff851690819055825190815291517fccfc7df822b68cdc8b0d7cd8b0255d24005c6fb4adc390a411ebdf309fa6dc099281900390910190a25050565b60607f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7600101805461070690612857565b6000611065336115d9565b61106f8383611e82565b9392505050565b61107f336115d9565b565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff1633146110f1576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec55565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604081205490819003611194576040517fa973256400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6111a7336111a283856128d9565b611f44565b60005b82811015610cb4578473ffffffffffffffffffffffffffffffffffffffff166323b872dd33308787868181106111e2576111e261292e565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e088901b16815273ffffffffffffffffffffffffffffffffffffffff958616600482015294909316602485015250602090910201356044820152606401600060405180830381600087803b15801561125e57600080fd5b505af1158015611272573d6000803e3d6000fd5b505050503361129e7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec90565b73ffffffffffffffffffffffffffffffffffffffff8716600090815260029190910160205260408120908686858181106112da576112da61292e565b90506020020135815260200190815260200160002060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550806113379061295d565b90506111aa565b61134d87878787878787611fbe565b156113dc5773ffffffffffffffffffffffffffffffffffffffff87811660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc60209081526040808320948b1680845294825291829020899055815189815291517f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9259281900390910190a35b50505050505050565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee602052604090206060906108349084846122f0565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff1633146114a7576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b807f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea3380547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff9283161790556040805133815291831660208301527fb532073b38c83145e3e5135377a08bf9aab55bc0fd7c1179cd4fb995d2a5159c910160405180910390a150565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c960205260408120805461106f907affffffffffffffffffffffffffffffffffffffffffffffffffffff8116907b01000000000000000000000000000000000000000000000000000000900464ffffffffff1661235b565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c96020526040902080547affffffffffffffffffffffffffffffffffffffffffffffffffffff8116907b01000000000000000000000000000000000000000000000000000000900464ffffffffff1681151580611670575080155b15610e45578115611695576000611687838361235b565b90506116938582611c5f565b505b50505073ffffffffffffffffffffffffffffffffffffffff1660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c96020526040902080547affffffffffffffffffffffffffffffffffffffffffffffffffffff167b0100000000000000000000000000000000000000000000000000000064ffffffffff421602179055565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc602090815260408083203384529091528120547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff81146117f7576117a68382612995565b73ffffffffffffffffffffffffffffffffffffffff861660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc602090815260408083203384529091529020555b73ffffffffffffffffffffffffffffffffffffffff851660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60205260408120805485929061184b908490612995565b909155505073ffffffffffffffffffffffffffffffffffffffff84811660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020908152604091829020805488019055905186815291928816917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a3506001949350505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff16331461107f576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8173ffffffffffffffffffffffffffffffffffffffff163b6000036119a0576040517f09ee12d500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc60001b8273ffffffffffffffffffffffffffffffffffffffff166352d1902d6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611a0f573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a3391906129ac565b14611a6a576040517f03ed501d00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805115611aed5760008273ffffffffffffffffffffffffffffffffffffffff1682604051611a9891906129c5565b600060405180830381855af49150503d8060008114611ad3576040519150601f19603f3d011682016040523d82523d6000602084013e611ad8565b606091505b5050905080611aeb573d6000803e3d6000fd5b505b60405173ffffffffffffffffffffffffffffffffffffffff8316907fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b90600090a2507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc80547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b611b9e826115d9565b73ffffffffffffffffffffffffffffffffffffffff821660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081208054839290611c0f9084907affffffffffffffffffffffffffffffffffffffffffffffffffffff166129e1565b92506101000a8154817affffffffffffffffffffffffffffffffffffffffffffffffffffff02191690837affffffffffffffffffffffffffffffffffffffffffffffffffffff1602179055505050565b807f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db76003016000828254611c939190612916565b909155505073ffffffffffffffffffffffffffffffffffffffff821660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60209081526040808320805486019055518481527fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a35050565b303b15611d51576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea3380547fffffffffffffffffffffffff00000000000000000000000000000000000000001633179055565b303b15611dd5576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7611e008482612a9a565b507f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db8611e2c8382612a9a565b507f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db980547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660ff929092169190911790555050565b3360009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020526040812080548391908390611ec2908490612995565b909155505073ffffffffffffffffffffffffffffffffffffffff831660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020908152604091829020805486019055905184815233917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910161080c565b611f4d826115d9565b73ffffffffffffffffffffffffffffffffffffffff821660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081208054839290611c0f9084907affffffffffffffffffffffffffffffffffffffffffffffffffffff16612bb4565b600042851015611ffa576040517f1ab7da6b00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff881660009081527f24034dbc71162a0a127c76a8ce123f10641be888cbac564cd2e6e6f5e2c19b81602052604081208054600180820190925591906120f2604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f60208201527f421979463954f2ac93264f1ce0c11a780b4a7686122abe11bac8c8244f44a3de918101919091527fc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc660608201524660808201523060a082015260009060c00160405160208183030381529060405280519060200120905090565b604080517f6e71edae12b1b97f4d1f60370fef10105fa2faae0126114a169c64845d6126c9602082015273ffffffffffffffffffffffffffffffffffffffff808f1692820192909252908c166060820152608081018b905260a0810185905260c081018a905260e001604051602081830303815290604052805190602001206040516020016121b39291907f190100000000000000000000000000000000000000000000000000000000000081526002810192909252602282015260420190565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08184030181528282528051602091820120600084529083018083525260ff891690820152606081018790526080810186905260a0016020604051602081039080840390855afa15801561222f573d6000803e3d6000fd5b50506040517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0015191505073ffffffffffffffffffffffffffffffffffffffff811615806122a957508973ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614155b156122e0576040517f815e1d6400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5060019998505050505050505050565b60405160208101600060018401815b8181101561234d5760008181526020899052604090205473ffffffffffffffffffffffffffffffffffffffff808916911603612345578084526020840193506001830192505b6001016122ff565b505082526040529392505050565b6000806123867f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec5490565b9050428184111561239c57600092505050610818565b818111156123a75750805b62015180662386f26fc10000866123be8785612995565b6123c891906128d9565b6123d291906128d9565b6123dc9190612bf3565b95945050505050565b60005b838110156124005781810151838201526020016123e8565b83811115610e455750506000910152565b60208152600082518060208401526124308160408501602087016123e5565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169190910160400192915050565b803573ffffffffffffffffffffffffffffffffffffffff8116811461248657600080fd5b919050565b6000806040838503121561249e57600080fd5b6124a783612462565b946020939093013593505050565b6000602082840312156124c757600080fd5b61106f82612462565b6000806000606084860312156124e557600080fd5b6124ee84612462565b92506124fc60208501612462565b9150604084013590509250925092565b60008083601f84011261251e57600080fd5b50813567ffffffffffffffff81111561253657600080fd5b60208301915083602082850101111561254e57600080fd5b9250929050565b60008060006040848603121561256a57600080fd5b61257384612462565b9250602084013567ffffffffffffffff81111561258f57600080fd5b61259b8682870161250c565b9497909650939450505050565b60008083601f8401126125ba57600080fd5b50813567ffffffffffffffff8111156125d257600080fd5b6020830191508360208260051b850101111561254e57600080fd5b60008060006040848603121561260257600080fd5b61260b84612462565b9250602084013567ffffffffffffffff81111561262757600080fd5b61259b868287016125a8565b6000806000806040858703121561264957600080fd5b843567ffffffffffffffff8082111561266157600080fd5b61266d888389016125a8565b9096509450602087013591508082111561268657600080fd5b50612693878288016125a8565b95989497509550505050565b600080600080604085870312156126b557600080fd5b843567ffffffffffffffff808211156126cd57600080fd5b6126d98883890161250c565b909650945060208701359150808211156126f257600080fd5b506126938782880161250c565b6000806040838503121561271257600080fd5b61271b83612462565b9150602083013578ffffffffffffffffffffffffffffffffffffffffffffffffff8116811461274957600080fd5b809150509250929050565b60006020828403121561276657600080fd5b5035919050565b600080600080600080600060e0888a03121561278857600080fd5b61279188612462565b965061279f60208901612462565b95506040880135945060608801359350608088013560ff811681146127c357600080fd5b9699959850939692959460a0840135945060c09093013592915050565b600080604083850312156127f357600080fd5b6127fc83612462565b915061280a60208401612462565b90509250929050565b6020808252825182820181905260009190848201906040850190845b8181101561284b5783518352928401929184019160010161282f565b50909695505050505050565b600181811c9082168061286b57607f821691505b6020821081036128a4577f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b50919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b6000817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0483118215151615612911576129116128aa565b500290565b60008219821115612929576129296128aa565b500190565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff820361298e5761298e6128aa565b5060010190565b6000828210156129a7576129a76128aa565b500390565b6000602082840312156129be57600080fd5b5051919050565b600082516129d78184602087016123e5565b9190910192915050565b60007affffffffffffffffffffffffffffffffffffffffffffffffffffff83811690831681811015612a1557612a156128aa565b039392505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b601f82111561095257600081815260208120601f850160051c81016020861015612a735750805b601f850160051c820191505b81811015612a9257828155600101612a7f565b505050505050565b815167ffffffffffffffff811115612ab457612ab4612a1d565b612ac881612ac28454612857565b84612a4c565b602080601f831160018114612b1b5760008415612ae55750858301515b7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600386901b1c1916600185901b178555612a92565b6000858152602081207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08616915b82811015612b6857888601518255948401946001909101908401612b49565b5085821015612ba457878501517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600388901b60f8161c191681555b5050505050600190811b01905550565b60007affffffffffffffffffffffffffffffffffffffffffffffffffffff808316818516808303821115612bea57612bea6128aa565b01949350505050565b600082612c29577f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b50049056fea2646970667358221220e94b1470d6900843ad91113afc161e67eecd3b07d0f7d4ae6887a9501529fbb764736f6c634300080f0033
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106101e55760003560e01c8063672434821161010f578063b88a802f116100a2578063dd62ed3e11610071578063dd62ed3e1461062d578063e4ab593d14610692578063f2fde38b146106b2578063f40f0f52146106c557600080fd5b8063b88a802f146105ec578063c5b41b89146105f4578063c9a3911e14610607578063d505accf1461061a57600080fd5b80637ecebe00116100de5780637ecebe001461053f5780638da5cb5b1461059457806395d89b41146105d1578063a9059cbb146105d957600080fd5b806367243482146104b15780637029144c146104c457806370a08231146104d75780637abdab561461052c57600080fd5b8063313ce567116101875780634f1ef286116101565780634f1ef2861461045a57806352d1902d1461046f5780635dbe4756146104775780635f36e2521461048a57600080fd5b8063313ce567146103585780633644e5151461038c5780633d9e7719146104345780634b0ee02a1461044757600080fd5b806318160ddd116101c357806318160ddd146102425780631f29d2dc14610269578063221ca18c146102f057806323b872dd1461034557600080fd5b806306fdde03146101ea578063095ea7b31461020857806316336c651461022b575b600080fd5b6101f26106d8565b6040516101ff9190612411565b60405180910390f35b61021b61021636600461248b565b610789565b60405190151581526020016101ff565b662386f26fc100005b6040519081526020016101ff565b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dba54610234565b6102cb61027736600461248b565b73ffffffffffffffffffffffffffffffffffffffff91821660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee6020908152604080832093835292905220541690565b60405173ffffffffffffffffffffffffffffffffffffffff90911681526020016101ff565b6102346102fe3660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604090205490565b61021b6103533660046124d0565b61081e565b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db95460405160ff90911681526020016101ff565b610234604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f60208201527f421979463954f2ac93264f1ce0c11a780b4a7686122abe11bac8c8244f44a3de918101919091527fc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc660608201524660808201523060a082015260009060c00160405160208183030381529060405280519060200120905090565b6102346104423660046124b5565b61083c565b6102346104553660046124b5565b6108b0565b61046d610468366004612555565b61090a565b005b610234610957565b61046d6104853660046125ed565b6109ed565b7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec54610234565b61046d6104bf366004612633565b610cbb565b61046d6104d236600461269f565b610d8e565b6102346104e53660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb602052604090205490565b61046d61053a3660046126ff565b610e4b565b61023461054d3660046124b5565b73ffffffffffffffffffffffffffffffffffffffff1660009081527f24034dbc71162a0a127c76a8ce123f10641be888cbac564cd2e6e6f5e2c19b81602052604090205490565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff166102cb565b6101f2611029565b61021b6105e736600461248b565b61105a565b61046d611076565b61046d610602366004612754565b611081565b61046d6106153660046125ed565b611115565b61046d61062836600461276d565b61133e565b61023461063b3660046127e0565b73ffffffffffffffffffffffffffffffffffffffff91821660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc6020908152604080832093909416825291909152205490565b6106a56106a03660046124d0565b6113e5565b6040516101ff9190612813565b61046d6106c03660046124b5565b611437565b6102346106d33660046124b5565b611545565b60607f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7805461070690612857565b80601f016020809104026020016040519081016040528092919081815260200182805461073290612857565b801561077f5780601f106107545761010080835404028352916020019161077f565b820191906000526020600020905b81548152906001019060200180831161076257829003601f168201915b5050505050905090565b3360008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc6020908152604080832073ffffffffffffffffffffffffffffffffffffffff871680855290835281842086905590518581529293909290917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591015b60405180910390a35060015b92915050565b6000610829846115d9565b610834848484611725565b949350505050565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081205461081890662386f26fc10000907affffffffffffffffffffffffffffffffffffffffffffffffffffff166128d9565b60006108bb82611545565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60205260409020546108189190612916565b6109126118df565b6109528383838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061194f92505050565b505050565b60003073ffffffffffffffffffffffffffffffffffffffff7f000000000000000000000000783f2136640c396805bf8488543abce4cf4cf87016146109c8576040517f0d89438e00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc90565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604081205490819003610a6c576040517fa973256400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610a7f33610a7a83856128d9565b611b95565b60005b82811015610cb45773ffffffffffffffffffffffffffffffffffffffff851660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee602052604081203391868685818110610ae257610ae261292e565b602090810292909201358352508101919091526040016000205473ffffffffffffffffffffffffffffffffffffffff1614610b49576040517f3a6bbed300000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff851660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee6020526040812090858584818110610ba057610ba061292e565b6020908102929092013583525081019190915260400160002080547fffffffffffffffffffffffff000000000000000000000000000000000000000016905573ffffffffffffffffffffffffffffffffffffffff85166323b872dd3033878786818110610c0f57610c0f61292e565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e088901b16815273ffffffffffffffffffffffffffffffffffffffff958616600482015294909316602485015250602090910201356044820152606401600060405180830381600087803b158015610c8b57600080fd5b505af1158015610c9f573d6000803e3d6000fd5b5050505080610cad9061295d565b9050610a82565b5050505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff163314610d2b576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b60005b83811015610cb457610d7e858583818110610d4b57610d4b61292e565b9050602002016020810190610d6091906124b5565b848484818110610d7257610d7261292e565b90506020020135611c5f565b610d878161295d565b9050610d2e565b303b15610dc7576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610dcf611d18565b610e4584848080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8801819004810282018101909252868152925086915085908190840183828082843760009201919091525060129250611d9c915050565b50505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff163314610ebb576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8078ffffffffffffffffffffffffffffffffffffffffffffffffff16600003610f10576040517f9c1b278400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff821660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604090205415610f8c576040517f41ab882d00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff821660008181527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602090815260409182902078ffffffffffffffffffffffffffffffffffffffffffffffffff851690819055825190815291517fccfc7df822b68cdc8b0d7cd8b0255d24005c6fb4adc390a411ebdf309fa6dc099281900390910190a25050565b60607f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7600101805461070690612857565b6000611065336115d9565b61106f8383611e82565b9392505050565b61107f336115d9565b565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff1633146110f1576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec55565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2faced602052604081205490819003611194576040517fa973256400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6111a7336111a283856128d9565b611f44565b60005b82811015610cb4578473ffffffffffffffffffffffffffffffffffffffff166323b872dd33308787868181106111e2576111e261292e565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e088901b16815273ffffffffffffffffffffffffffffffffffffffff958616600482015294909316602485015250602090910201356044820152606401600060405180830381600087803b15801561125e57600080fd5b505af1158015611272573d6000803e3d6000fd5b505050503361129e7f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec90565b73ffffffffffffffffffffffffffffffffffffffff8716600090815260029190910160205260408120908686858181106112da576112da61292e565b90506020020135815260200190815260200160002060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550806113379061295d565b90506111aa565b61134d87878787878787611fbe565b156113dc5773ffffffffffffffffffffffffffffffffffffffff87811660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc60209081526040808320948b1680845294825291829020899055815189815291517f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9259281900390910190a35b50505050505050565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facee602052604090206060906108349084846122f0565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff1633146114a7576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b807f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea3380547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff9283161790556040805133815291831660208301527fb532073b38c83145e3e5135377a08bf9aab55bc0fd7c1179cd4fb995d2a5159c910160405180910390a150565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c960205260408120805461106f907affffffffffffffffffffffffffffffffffffffffffffffffffffff8116907b01000000000000000000000000000000000000000000000000000000900464ffffffffff1661235b565b73ffffffffffffffffffffffffffffffffffffffff811660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c96020526040902080547affffffffffffffffffffffffffffffffffffffffffffffffffffff8116907b01000000000000000000000000000000000000000000000000000000900464ffffffffff1681151580611670575080155b15610e45578115611695576000611687838361235b565b90506116938582611c5f565b505b50505073ffffffffffffffffffffffffffffffffffffffff1660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c96020526040902080547affffffffffffffffffffffffffffffffffffffffffffffffffffff167b0100000000000000000000000000000000000000000000000000000064ffffffffff421602179055565b73ffffffffffffffffffffffffffffffffffffffff831660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc602090815260408083203384529091528120547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff81146117f7576117a68382612995565b73ffffffffffffffffffffffffffffffffffffffff861660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbc602090815260408083203384529091529020555b73ffffffffffffffffffffffffffffffffffffffff851660009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60205260408120805485929061184b908490612995565b909155505073ffffffffffffffffffffffffffffffffffffffff84811660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020908152604091829020805488019055905186815291928816917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a3506001949350505050565b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea335473ffffffffffffffffffffffffffffffffffffffff16331461107f576040517f5cd8319200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8173ffffffffffffffffffffffffffffffffffffffff163b6000036119a0576040517f09ee12d500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc60001b8273ffffffffffffffffffffffffffffffffffffffff166352d1902d6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611a0f573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a3391906129ac565b14611a6a576040517f03ed501d00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805115611aed5760008273ffffffffffffffffffffffffffffffffffffffff1682604051611a9891906129c5565b600060405180830381855af49150503d8060008114611ad3576040519150601f19603f3d011682016040523d82523d6000602084013e611ad8565b606091505b5050905080611aeb573d6000803e3d6000fd5b505b60405173ffffffffffffffffffffffffffffffffffffffff8316907fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b90600090a2507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc80547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b611b9e826115d9565b73ffffffffffffffffffffffffffffffffffffffff821660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081208054839290611c0f9084907affffffffffffffffffffffffffffffffffffffffffffffffffffff166129e1565b92506101000a8154817affffffffffffffffffffffffffffffffffffffffffffffffffffff02191690837affffffffffffffffffffffffffffffffffffffffffffffffffffff1602179055505050565b807f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db76003016000828254611c939190612916565b909155505073ffffffffffffffffffffffffffffffffffffffff821660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb60209081526040808320805486019055518481527fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a35050565b303b15611d51576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f87917b04fc43108fc3d291ac961b425fe1ddcf80087b2cb7e3c48f3e9233ea3380547fffffffffffffffffffffffff00000000000000000000000000000000000000001633179055565b303b15611dd5576040517f0dc149f000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b7f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db7611e008482612a9a565b507f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db8611e2c8382612a9a565b507f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80db980547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff001660ff929092169190911790555050565b3360009081527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020526040812080548391908390611ec2908490612995565b909155505073ffffffffffffffffffffffffffffffffffffffff831660008181527f0e539be85842d1c3b5b43263a827c1e07ab5a9c9536bf840ece723e480d80dbb6020908152604091829020805486019055905184815233917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910161080c565b611f4d826115d9565b73ffffffffffffffffffffffffffffffffffffffff821660009081527f2bf76f1229f14879252da90846a528ce52c56d0ade153f3ef6c5b45141fb99c9602052604081208054839290611c0f9084907affffffffffffffffffffffffffffffffffffffffffffffffffffff16612bb4565b600042851015611ffa576040517f1ab7da6b00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b73ffffffffffffffffffffffffffffffffffffffff881660009081527f24034dbc71162a0a127c76a8ce123f10641be888cbac564cd2e6e6f5e2c19b81602052604081208054600180820190925591906120f2604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f60208201527f421979463954f2ac93264f1ce0c11a780b4a7686122abe11bac8c8244f44a3de918101919091527fc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc660608201524660808201523060a082015260009060c00160405160208183030381529060405280519060200120905090565b604080517f6e71edae12b1b97f4d1f60370fef10105fa2faae0126114a169c64845d6126c9602082015273ffffffffffffffffffffffffffffffffffffffff808f1692820192909252908c166060820152608081018b905260a0810185905260c081018a905260e001604051602081830303815290604052805190602001206040516020016121b39291907f190100000000000000000000000000000000000000000000000000000000000081526002810192909252602282015260420190565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08184030181528282528051602091820120600084529083018083525260ff891690820152606081018790526080810186905260a0016020604051602081039080840390855afa15801561222f573d6000803e3d6000fd5b50506040517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0015191505073ffffffffffffffffffffffffffffffffffffffff811615806122a957508973ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614155b156122e0576040517f815e1d6400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5060019998505050505050505050565b60405160208101600060018401815b8181101561234d5760008181526020899052604090205473ffffffffffffffffffffffffffffffffffffffff808916911603612345578084526020840193506001830192505b6001016122ff565b505082526040529392505050565b6000806123867f1a092854511578a55ddb9a3e239e5eb710da1c5cb2adb4c4d5c3fe3a7e2facec5490565b9050428184111561239c57600092505050610818565b818111156123a75750805b62015180662386f26fc10000866123be8785612995565b6123c891906128d9565b6123d291906128d9565b6123dc9190612bf3565b95945050505050565b60005b838110156124005781810151838201526020016123e8565b83811115610e455750506000910152565b60208152600082518060208401526124308160408501602087016123e5565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169190910160400192915050565b803573ffffffffffffffffffffffffffffffffffffffff8116811461248657600080fd5b919050565b6000806040838503121561249e57600080fd5b6124a783612462565b946020939093013593505050565b6000602082840312156124c757600080fd5b61106f82612462565b6000806000606084860312156124e557600080fd5b6124ee84612462565b92506124fc60208501612462565b9150604084013590509250925092565b60008083601f84011261251e57600080fd5b50813567ffffffffffffffff81111561253657600080fd5b60208301915083602082850101111561254e57600080fd5b9250929050565b60008060006040848603121561256a57600080fd5b61257384612462565b9250602084013567ffffffffffffffff81111561258f57600080fd5b61259b8682870161250c565b9497909650939450505050565b60008083601f8401126125ba57600080fd5b50813567ffffffffffffffff8111156125d257600080fd5b6020830191508360208260051b850101111561254e57600080fd5b60008060006040848603121561260257600080fd5b61260b84612462565b9250602084013567ffffffffffffffff81111561262757600080fd5b61259b868287016125a8565b6000806000806040858703121561264957600080fd5b843567ffffffffffffffff8082111561266157600080fd5b61266d888389016125a8565b9096509450602087013591508082111561268657600080fd5b50612693878288016125a8565b95989497509550505050565b600080600080604085870312156126b557600080fd5b843567ffffffffffffffff808211156126cd57600080fd5b6126d98883890161250c565b909650945060208701359150808211156126f257600080fd5b506126938782880161250c565b6000806040838503121561271257600080fd5b61271b83612462565b9150602083013578ffffffffffffffffffffffffffffffffffffffffffffffffff8116811461274957600080fd5b809150509250929050565b60006020828403121561276657600080fd5b5035919050565b600080600080600080600060e0888a03121561278857600080fd5b61279188612462565b965061279f60208901612462565b95506040880135945060608801359350608088013560ff811681146127c357600080fd5b9699959850939692959460a0840135945060c09093013592915050565b600080604083850312156127f357600080fd5b6127fc83612462565b915061280a60208401612462565b90509250929050565b6020808252825182820181905260009190848201906040850190845b8181101561284b5783518352928401929184019160010161282f565b50909695505050505050565b600181811c9082168061286b57607f821691505b6020821081036128a4577f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b50919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b6000817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0483118215151615612911576129116128aa565b500290565b60008219821115612929576129296128aa565b500190565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff820361298e5761298e6128aa565b5060010190565b6000828210156129a7576129a76128aa565b500390565b6000602082840312156129be57600080fd5b5051919050565b600082516129d78184602087016123e5565b9190910192915050565b60007affffffffffffffffffffffffffffffffffffffffffffffffffffff83811690831681811015612a1557612a156128aa565b039392505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b601f82111561095257600081815260208120601f850160051c81016020861015612a735750805b601f850160051c820191505b81811015612a9257828155600101612a7f565b505050505050565b815167ffffffffffffffff811115612ab457612ab4612a1d565b612ac881612ac28454612857565b84612a4c565b602080601f831160018114612b1b5760008415612ae55750858301515b7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600386901b1c1916600185901b178555612a92565b6000858152602081207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08616915b82811015612b6857888601518255948401946001909101908401612b49565b5085821015612ba457878501517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600388901b60f8161c191681555b5050505050600190811b01905550565b60007affffffffffffffffffffffffffffffffffffffffffffffffffffff808316818516808303821115612bea57612bea6128aa565b01949350505050565b600082612c29577f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b50049056fea2646970667358221220e94b1470d6900843ad91113afc161e67eecd3b07d0f7d4ae6887a9501529fbb764736f6c634300080f0033
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 30 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|
Loading...
Loading
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.