Feature Tip: Add private address tag to any address under My Name Tag !
Overview
ETH Balance
0 ETH
Eth Value
$0.00Latest 25 from a total of 67 transactions
| Transaction Hash |
Method
|
Block
|
From
|
|
To
|
||||
|---|---|---|---|---|---|---|---|---|---|
| Multicall | 23939935 | 6 days ago | IN | 0 ETH | 0.00000327 | ||||
| Set Contenthash | 23928806 | 7 days ago | IN | 0 ETH | 0.00000355 | ||||
| Multicall | 23869061 | 16 days ago | IN | 0 ETH | 0.00014907 | ||||
| Set Addr | 23868478 | 16 days ago | IN | 0 ETH | 0.00000475 | ||||
| Multicall | 23847310 | 19 days ago | IN | 0 ETH | 0.00019546 | ||||
| Multicall | 23829179 | 21 days ago | IN | 0 ETH | 0.00000503 | ||||
| Multicall | 23828983 | 21 days ago | IN | 0 ETH | 0.00000624 | ||||
| Multicall | 23828272 | 22 days ago | IN | 0 ETH | 0.00000795 | ||||
| Set Text | 23769331 | 30 days ago | IN | 0 ETH | 0.00010717 | ||||
| Multicall | 23749956 | 32 days ago | IN | 0 ETH | 0.00016527 | ||||
| Set Addr | 23744197 | 33 days ago | IN | 0 ETH | 0.00002391 | ||||
| Multicall | 23744188 | 33 days ago | IN | 0 ETH | 0.00002869 | ||||
| Multicall | 23744172 | 33 days ago | IN | 0 ETH | 0.00023708 | ||||
| Multicall | 23735909 | 34 days ago | IN | 0 ETH | 0.00003971 | ||||
| Multicall | 23735884 | 34 days ago | IN | 0 ETH | 0.00005074 | ||||
| Multicall | 23731797 | 35 days ago | IN | 0 ETH | 0.0000286 | ||||
| Multicall | 23729553 | 35 days ago | IN | 0 ETH | 0.00005083 | ||||
| Multicall | 23729278 | 35 days ago | IN | 0 ETH | 0.0000708 | ||||
| Set Contenthash | 23683548 | 42 days ago | IN | 0 ETH | 0.00003031 | ||||
| Multicall | 23597468 | 54 days ago | IN | 0 ETH | 0.00059599 | ||||
| Set Addr | 23574939 | 57 days ago | IN | 0 ETH | 0.00003214 | ||||
| Set Resolution T... | 23574799 | 57 days ago | IN | 0 ETH | 0.00007244 | ||||
| Multicall | 23532344 | 63 days ago | IN | 0 ETH | 0.00009014 | ||||
| Multicall | 23454257 | 74 days ago | IN | 0 ETH | 0.00007963 | ||||
| Set Contenthash | 23388238 | 83 days ago | IN | 0 ETH | 0.00001516 |
Latest 1 internal transaction
Advanced mode:
| Parent Transaction Hash | Method | Block |
From
|
|
To
|
||
|---|---|---|---|---|---|---|---|
| 0x604060c0 | 22026908 | 273 days ago | Contract Creation | 0 ETH |
Loading...
Loading
Cross-Chain Transactions
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 Source Code Verified (Exact Match)
Contract Name:
NamespaceHybridResolver
Compiler Version
v0.8.24+commit.e11b9ed9
Optimization Enabled:
Yes with 200 runs
Other Settings:
paris EvmVersion
Contract Source Code (Solidity Standard Json-Input format)
// @author artii.eth
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
import {IExtendedResolver} from "@ensdomains/ens-contracts/contracts/resolvers/profiles/IExtendedResolver.sol";
import {BytesUtils} from "@ensdomains/ens-contracts/contracts/utils/BytesUtils.sol";
import {EnsResolverBase} from "./EnsResolverBase.sol";
import {ENS} from "@ensdomains/ens-contracts/contracts/registry/ENS.sol";
import {OffchainResolver} from "./OffchainResolver.sol";
import {Ownable} from "@openzeppelin/contracts/access/Ownable.sol";
import "./Types.sol";
contract NamespaceHybridResolver is
IExtendedResolver,
EnsResolverBase,
OffchainResolver
{
using BytesUtils for bytes;
address public defaultFallbackResolver;
mapping(bytes32 => address) public fallbackResolvers;
mapping(bytes32 => bool) private emptyResponseHashes;
mapping(bytes32 => ResolutionConfig) public configs;
mapping(uint => bool) supportedResolutionTypes;
mapping(uint => string[]) public resolutionUrls;
event ResolutionConfigChanged(bytes32 node, uint prevType, uint newType);
event FallbackResolverSet(bytes32 node, address newResolver);
event ResolutionUrlsChanged(uint resolutionType, string[] urls);
constructor(
address[] memory _signers,
address ens,
address nameWrapper,
address _fallbackResolver
)
Ownable(_msgSender())
EnsResolverBase(ens, nameWrapper)
OffchainResolver(_signers)
{
emptyResponseHashes[
0x290decd9548b62a8d60345a988386fc84ba6bc95484008f6362f93160ef3e563
] = true;
emptyResponseHashes[
0x569e75fc77c1a856f6daaf9e69d8a9566ca34aa47f9133711ce065a571af0cfd
] = true;
supportedResolutionTypes[OFFCHAIN_DB_RESOLUTION] = true;
supportedResolutionTypes[BASE_RESOLUTION] = true;
supportedResolutionTypes[OP_RESOLUTION] = true;
defaultFallbackResolver = _fallbackResolver;
}
function resolve(
bytes memory dnsName,
bytes memory data
)
public
view
override(IExtendedResolver, EnsResolverBase)
returns (bytes memory)
{
bytes32 node = dnsName.namehash(0);
if (isNameOnchain(node) && !configs[node].resolveOffchain) {
return resolveOnchain(node, data);
}
resolveOffchain(dnsName, data);
}
function resolveOffchain(
bytes memory dnsName,
bytes memory data
) internal view {
// Finding the configured resultion type for provided name
// and default to offchain_db_resolution if its not set by a name owner
uint resolutionType = getResolutionConfigurationForName(dnsName);
if (resolutionType == 0) {
resolutionType = OFFCHAIN_DB_RESOLUTION;
}
string[] memory resolutionsUrls = resolutionUrls[resolutionType];
require(resolutionsUrls.length > 0, "No resoultion urls found");
_resolveOffchain(dnsName, data, resolutionsUrls);
}
function resolveOnchain(
bytes32 node,
bytes memory data
) internal view returns (bytes memory) {
// first we will try to resolve the request on current smart contract
(bool success, bytes memory result) = address(this).staticcall(data);
if (success && !isEmptyResponse(result)) {
return result;
}
// We will then try to resolve data from the configured fallback resolver
// this was set so that we do not need to transfer records.
// if the fallback resolver was not set for name, we'll default to
// current ENS Public resolver
address fallbackResolver = getFallbackResolver(node);
(bool fallbackSuccess, bytes memory fallbackResult) = address(
fallbackResolver
).staticcall(data);
require(
fallbackSuccess,
"Could not query the fallback resolver contract"
);
return fallbackResult;
}
function getFallbackResolver(bytes32 node) internal view returns (address) {
address fallbackResolver = fallbackResolvers[node];
return
fallbackResolver == address(0)
? defaultFallbackResolver
: fallbackResolver;
}
function setResolutionType(
bytes32 node,
uint newResolutionType
) public isNodeOwner(node) {
require(
supportedResolutionTypes[newResolutionType],
"Unsupported resolution type provided"
);
uint prevResolutionType = configs[node].resolutionType;
configs[node].resolutionType = newResolutionType;
emit ResolutionConfigChanged(
node,
prevResolutionType,
newResolutionType
);
}
function setFallbackResolver(
bytes32 node,
address fallbackResolver
) public isNodeOwner(node) {
require(
fallbackResolvers[node] != fallbackResolver,
"Same fallback resolver already set"
);
fallbackResolvers[node] = fallbackResolver;
emit FallbackResolverSet(node, fallbackResolver);
}
function isEmptyResponse(
bytes memory response
) internal view returns (bool) {
bytes32 responseHash = keccak256(response);
return emptyResponseHashes[responseHash];
}
function isNameOnchain(bytes32 node) internal view returns (bool) {
// Subnames which are resolvable offchain/l2 will not have
// a resolver set, since they do not exist on L1
return ens.resolver(node) != address(0);
}
function extractDnsParent(
bytes memory dnsName
) internal pure returns (bytes memory) {
uint256 idx = 0;
// Find the first label's length
uint256 labelLength = uint8(dnsName[idx]);
// Advance the index to skip the first label and its length byte
idx += labelLength + 1;
// Create a new `bytes` array for the remainder
bytes memory parent = new bytes(dnsName.length - idx);
for (uint256 i = 0; i < parent.length; i++) {
parent[i] = dnsName[idx + i];
}
return parent;
}
function getResolutionConfigurationForName(
bytes memory dnsName
) internal view returns (uint) {
bytes memory current = dnsName;
bytes32 nameHash = current.namehash(0);
while (nameHash != bytes32(0)) {
if (configs[nameHash].resolutionType != 0) {
return configs[nameHash].resolutionType;
} else {
current = extractDnsParent(current);
nameHash = current.namehash(0);
}
}
return 0;
}
function setResolutionUrls(
uint256 resolutionType,
string[] memory urls
) public onlyOwner {
resolutionUrls[resolutionType] = urls;
emit ResolutionUrlsChanged(resolutionType, urls);
}
function setSupportedResolutionType(
uint resolutionType,
bool supported
) public onlyOwner {
supportedResolutionTypes[resolutionType] = supported;
}
function setEmptyResponse(bytes32 hash, bool value) public onlyOwner {
emptyResponseHashes[hash] = value;
}
function setDefaultFallbackResolver(
address _fallbackResolver
) public onlyOwner {
defaultFallbackResolver = _fallbackResolver;
}
}import "../registry/ENS.sol";
import "./IBaseRegistrar.sol";
import "@openzeppelin/contracts/token/ERC721/IERC721.sol";
interface IBaseRegistrar is IERC721 {
event ControllerAdded(address indexed controller);
event ControllerRemoved(address indexed controller);
event NameMigrated(
uint256 indexed id,
address indexed owner,
uint256 expires
);
event NameRegistered(
uint256 indexed id,
address indexed owner,
uint256 expires
);
event NameRenewed(uint256 indexed id, uint256 expires);
// Authorises a controller, who can register and renew domains.
function addController(address controller) external;
// Revoke controller permission for an address.
function removeController(address controller) external;
// Set the resolver for the TLD this registrar manages.
function setResolver(address resolver) external;
// Returns the expiration timestamp of the specified label hash.
function nameExpires(uint256 id) external view returns (uint256);
// Returns true if the specified name is available for registration.
function available(uint256 id) external view returns (bool);
/**
* @dev Register a name.
*/
function register(
uint256 id,
address owner,
uint256 duration
) external returns (uint256);
function renew(uint256 id, uint256 duration) external returns (uint256);
/**
* @dev Reclaim ownership of a name in ENS, if you own it in the registrar.
*/
function reclaim(uint256 id, address owner) external;
}//SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface ENS {
// Logged when the owner of a node assigns a new owner to a subnode.
event NewOwner(bytes32 indexed node, bytes32 indexed label, address owner);
// Logged when the owner of a node transfers ownership to a new account.
event Transfer(bytes32 indexed node, address owner);
// Logged when the resolver for a node changes.
event NewResolver(bytes32 indexed node, address resolver);
// Logged when the TTL of a node changes
event NewTTL(bytes32 indexed node, uint64 ttl);
// Logged when an operator is added or removed.
event ApprovalForAll(
address indexed owner,
address indexed operator,
bool approved
);
function setRecord(
bytes32 node,
address owner,
address resolver,
uint64 ttl
) external;
function setSubnodeRecord(
bytes32 node,
bytes32 label,
address owner,
address resolver,
uint64 ttl
) external;
function setSubnodeOwner(
bytes32 node,
bytes32 label,
address owner
) external returns (bytes32);
function setResolver(bytes32 node, address resolver) external;
function setOwner(bytes32 node, address owner) external;
function setTTL(bytes32 node, uint64 ttl) external;
function setApprovalForAll(address operator, bool approved) external;
function owner(bytes32 node) external view returns (address);
function resolver(bytes32 node) external view returns (address);
function ttl(bytes32 node) external view returns (uint64);
function recordExists(bytes32 node) external view returns (bool);
function isApprovedForAll(
address owner,
address operator
) external view returns (bool);
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;
interface IMulticallable {
function multicall(
bytes[] calldata data
) external returns (bytes[] memory results);
function multicallWithNodeCheck(
bytes32,
bytes[] calldata data
) external returns (bytes[] memory results);
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;
import "./IMulticallable.sol";
import "@openzeppelin/contracts/utils/introspection/ERC165.sol";
abstract contract Multicallable is IMulticallable, ERC165 {
function _multicall(
bytes32 nodehash,
bytes[] calldata data
) internal returns (bytes[] memory results) {
results = new bytes[](data.length);
for (uint256 i = 0; i < data.length; i++) {
if (nodehash != bytes32(0)) {
bytes32 txNamehash = bytes32(data[i][4:36]);
require(
txNamehash == nodehash,
"multicall: All records must have a matching namehash"
);
}
(bool success, bytes memory result) = address(this).delegatecall(
data[i]
);
require(success);
results[i] = result;
}
return results;
}
// This function provides an extra security check when called
// from priviledged contracts (such as EthRegistrarController)
// that can set records on behalf of the node owners
function multicallWithNodeCheck(
bytes32 nodehash,
bytes[] calldata data
) external returns (bytes[] memory results) {
return _multicall(nodehash, data);
}
function multicall(
bytes[] calldata data
) public override returns (bytes[] memory results) {
return _multicall(bytes32(0), data);
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IMulticallable).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "./IABIResolver.sol";
import "../ResolverBase.sol";
abstract contract ABIResolver is IABIResolver, ResolverBase {
mapping(uint64 => mapping(bytes32 => mapping(uint256 => bytes))) versionable_abis;
/**
* Sets the ABI associated with an ENS node.
* Nodes may have one ABI of each content type. To remove an ABI, set it to
* the empty string.
* @param node The node to update.
* @param contentType The content type of the ABI
* @param data The ABI data.
*/
function setABI(
bytes32 node,
uint256 contentType,
bytes calldata data
) external virtual authorised(node) {
// Content types must be powers of 2
require(((contentType - 1) & contentType) == 0);
versionable_abis[recordVersions[node]][node][contentType] = data;
emit ABIChanged(node, contentType);
}
/**
* Returns the ABI associated with an ENS node.
* Defined in EIP205.
* @param node The ENS node to query
* @param contentTypes A bitwise OR of the ABI formats accepted by the caller.
* @return contentType The content type of the return value
* @return data The ABI data
*/
function ABI(
bytes32 node,
uint256 contentTypes
) external view virtual override returns (uint256, bytes memory) {
mapping(uint256 => bytes) storage abiset = versionable_abis[
recordVersions[node]
][node];
for (
uint256 contentType = 1;
contentType <= contentTypes;
contentType <<= 1
) {
if (
(contentType & contentTypes) != 0 &&
abiset[contentType].length > 0
) {
return (contentType, abiset[contentType]);
}
}
return (0, bytes(""));
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IABIResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "../ResolverBase.sol";
import "./IAddrResolver.sol";
import "./IAddressResolver.sol";
abstract contract AddrResolver is
IAddrResolver,
IAddressResolver,
ResolverBase
{
uint256 private constant COIN_TYPE_ETH = 60;
mapping(uint64 => mapping(bytes32 => mapping(uint256 => bytes))) versionable_addresses;
/**
* Sets the address associated with an ENS node.
* May only be called by the owner of that node in the ENS registry.
* @param node The node to update.
* @param a The address to set.
*/
function setAddr(
bytes32 node,
address a
) external virtual authorised(node) {
setAddr(node, COIN_TYPE_ETH, addressToBytes(a));
}
/**
* Returns the address associated with an ENS node.
* @param node The ENS node to query.
* @return The associated address.
*/
function addr(
bytes32 node
) public view virtual override returns (address payable) {
bytes memory a = addr(node, COIN_TYPE_ETH);
if (a.length == 0) {
return payable(0);
}
return bytesToAddress(a);
}
function setAddr(
bytes32 node,
uint256 coinType,
bytes memory a
) public virtual authorised(node) {
emit AddressChanged(node, coinType, a);
if (coinType == COIN_TYPE_ETH) {
emit AddrChanged(node, bytesToAddress(a));
}
versionable_addresses[recordVersions[node]][node][coinType] = a;
}
function addr(
bytes32 node,
uint256 coinType
) public view virtual override returns (bytes memory) {
return versionable_addresses[recordVersions[node]][node][coinType];
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IAddrResolver).interfaceId ||
interfaceID == type(IAddressResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
function bytesToAddress(
bytes memory b
) internal pure returns (address payable a) {
require(b.length == 20);
assembly {
a := div(mload(add(b, 32)), exp(256, 12))
}
}
function addressToBytes(address a) internal pure returns (bytes memory b) {
b = new bytes(20);
assembly {
mstore(add(b, 32), mul(a, exp(256, 12)))
}
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "../ResolverBase.sol";
import "./IContentHashResolver.sol";
abstract contract ContentHashResolver is IContentHashResolver, ResolverBase {
mapping(uint64 => mapping(bytes32 => bytes)) versionable_hashes;
/**
* Sets the contenthash associated with an ENS node.
* May only be called by the owner of that node in the ENS registry.
* @param node The node to update.
* @param hash The contenthash to set
*/
function setContenthash(
bytes32 node,
bytes calldata hash
) external virtual authorised(node) {
versionable_hashes[recordVersions[node]][node] = hash;
emit ContenthashChanged(node, hash);
}
/**
* Returns the contenthash associated with an ENS node.
* @param node The ENS node to query.
* @return The associated contenthash.
*/
function contenthash(
bytes32 node
) external view virtual override returns (bytes memory) {
return versionable_hashes[recordVersions[node]][node];
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IContentHashResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface IABIResolver {
event ABIChanged(bytes32 indexed node, uint256 indexed contentType);
/**
* Returns the ABI associated with an ENS node.
* Defined in EIP205.
* @param node The ENS node to query
* @param contentTypes A bitwise OR of the ABI formats accepted by the caller.
* @return contentType The content type of the return value
* @return data The ABI data
*/
function ABI(
bytes32 node,
uint256 contentTypes
) external view returns (uint256, bytes memory);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
/**
* Interface for the new (multicoin) addr function.
*/
interface IAddressResolver {
event AddressChanged(
bytes32 indexed node,
uint256 coinType,
bytes newAddress
);
function addr(
bytes32 node,
uint256 coinType
) external view returns (bytes memory);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
/**
* Interface for the legacy (ETH-only) addr function.
*/
interface IAddrResolver {
event AddrChanged(bytes32 indexed node, address a);
/**
* Returns the address associated with an ENS node.
* @param node The ENS node to query.
* @return The associated address.
*/
function addr(bytes32 node) external view returns (address payable);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface IContentHashResolver {
event ContenthashChanged(bytes32 indexed node, bytes hash);
/**
* Returns the contenthash associated with an ENS node.
* @param node The ENS node to query.
* @return The associated contenthash.
*/
function contenthash(bytes32 node) external view returns (bytes memory);
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;
interface IExtendedResolver {
function resolve(
bytes memory name,
bytes memory data
) external view returns (bytes memory);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface IInterfaceResolver {
event InterfaceChanged(
bytes32 indexed node,
bytes4 indexed interfaceID,
address implementer
);
/**
* Returns the address of a contract that implements the specified interface for this name.
* If an implementer has not been set for this interfaceID and name, the resolver will query
* the contract at `addr()`. If `addr()` is set, a contract exists at that address, and that
* contract implements EIP165 and returns `true` for the specified interfaceID, its address
* will be returned.
* @param node The ENS node to query.
* @param interfaceID The EIP 165 interface ID to check for.
* @return The address that implements this interface, or 0 if the interface is unsupported.
*/
function interfaceImplementer(
bytes32 node,
bytes4 interfaceID
) external view returns (address);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface INameResolver {
event NameChanged(bytes32 indexed node, string name);
/**
* Returns the name associated with an ENS node, for reverse records.
* Defined in EIP181.
* @param node The ENS node to query.
* @return The associated name.
*/
function name(bytes32 node) external view returns (string memory);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "@openzeppelin/contracts/utils/introspection/IERC165.sol";
import "../ResolverBase.sol";
import "./AddrResolver.sol";
import "./IInterfaceResolver.sol";
abstract contract InterfaceResolver is IInterfaceResolver, AddrResolver {
mapping(uint64 => mapping(bytes32 => mapping(bytes4 => address))) versionable_interfaces;
/**
* Sets an interface associated with a name.
* Setting the address to 0 restores the default behaviour of querying the contract at `addr()` for interface support.
* @param node The node to update.
* @param interfaceID The EIP 165 interface ID.
* @param implementer The address of a contract that implements this interface for this node.
*/
function setInterface(
bytes32 node,
bytes4 interfaceID,
address implementer
) external virtual authorised(node) {
versionable_interfaces[recordVersions[node]][node][
interfaceID
] = implementer;
emit InterfaceChanged(node, interfaceID, implementer);
}
/**
* Returns the address of a contract that implements the specified interface for this name.
* If an implementer has not been set for this interfaceID and name, the resolver will query
* the contract at `addr()`. If `addr()` is set, a contract exists at that address, and that
* contract implements EIP165 and returns `true` for the specified interfaceID, its address
* will be returned.
* @param node The ENS node to query.
* @param interfaceID The EIP 165 interface ID to check for.
* @return The address that implements this interface, or 0 if the interface is unsupported.
*/
function interfaceImplementer(
bytes32 node,
bytes4 interfaceID
) external view virtual override returns (address) {
address implementer = versionable_interfaces[recordVersions[node]][
node
][interfaceID];
if (implementer != address(0)) {
return implementer;
}
address a = addr(node);
if (a == address(0)) {
return address(0);
}
(bool success, bytes memory returnData) = a.staticcall(
abi.encodeWithSignature(
"supportsInterface(bytes4)",
type(IERC165).interfaceId
)
);
if (!success || returnData.length < 32 || returnData[31] == 0) {
// EIP 165 not supported by target
return address(0);
}
(success, returnData) = a.staticcall(
abi.encodeWithSignature("supportsInterface(bytes4)", interfaceID)
);
if (!success || returnData.length < 32 || returnData[31] == 0) {
// Specified interface not supported by target
return address(0);
}
return a;
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IInterfaceResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface ITextResolver {
event TextChanged(
bytes32 indexed node,
string indexed indexedKey,
string key,
string value
);
/**
* Returns the text data associated with an ENS node and key.
* @param node The ENS node to query.
* @param key The text data key to query.
* @return The associated text data.
*/
function text(
bytes32 node,
string calldata key
) external view returns (string memory);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
interface IVersionableResolver {
event VersionChanged(bytes32 indexed node, uint64 newVersion);
function recordVersions(bytes32 node) external view returns (uint64);
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "../ResolverBase.sol";
import "./INameResolver.sol";
abstract contract NameResolver is INameResolver, ResolverBase {
mapping(uint64 => mapping(bytes32 => string)) versionable_names;
/**
* Sets the name associated with an ENS node, for reverse records.
* May only be called by the owner of that node in the ENS registry.
* @param node The node to update.
*/
function setName(
bytes32 node,
string calldata newName
) external virtual authorised(node) {
versionable_names[recordVersions[node]][node] = newName;
emit NameChanged(node, newName);
}
/**
* Returns the name associated with an ENS node, for reverse records.
* Defined in EIP181.
* @param node The ENS node to query.
* @return The associated name.
*/
function name(
bytes32 node
) external view virtual override returns (string memory) {
return versionable_names[recordVersions[node]][node];
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(INameResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "../ResolverBase.sol";
import "./ITextResolver.sol";
abstract contract TextResolver is ITextResolver, ResolverBase {
mapping(uint64 => mapping(bytes32 => mapping(string => string))) versionable_texts;
/**
* Sets the text data associated with an ENS node and key.
* May only be called by the owner of that node in the ENS registry.
* @param node The node to update.
* @param key The key to set.
* @param value The text data value to set.
*/
function setText(
bytes32 node,
string calldata key,
string calldata value
) external virtual authorised(node) {
versionable_texts[recordVersions[node]][node][key] = value;
emit TextChanged(node, key, key, value);
}
/**
* Returns the text data associated with an ENS node and key.
* @param node The ENS node to query.
* @param key The text data key to query.
* @return The associated text data.
*/
function text(
bytes32 node,
string calldata key
) external view virtual override returns (string memory) {
return versionable_texts[recordVersions[node]][node][key];
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(ITextResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.8.4;
import "@openzeppelin/contracts/utils/introspection/ERC165.sol";
import "./profiles/IVersionableResolver.sol";
abstract contract ResolverBase is ERC165, IVersionableResolver {
mapping(bytes32 => uint64) public recordVersions;
function isAuthorised(bytes32 node) internal view virtual returns (bool);
modifier authorised(bytes32 node) {
require(isAuthorised(node));
_;
}
/**
* Increments the record version associated with an ENS node.
* May only be called by the owner of that node in the ENS registry.
* @param node The node to update.
*/
function clearRecords(bytes32 node) public virtual authorised(node) {
recordVersions[node]++;
emit VersionChanged(node, recordVersions[node]);
}
function supportsInterface(
bytes4 interfaceID
) public view virtual override returns (bool) {
return
interfaceID == type(IVersionableResolver).interfaceId ||
super.supportsInterface(interfaceID);
}
}//SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;
library BytesUtils {
error OffsetOutOfBoundsError(uint256 offset, uint256 length);
/*
* @dev Returns the keccak-256 hash of a byte range.
* @param self The byte string to hash.
* @param offset The position to start hashing at.
* @param len The number of bytes to hash.
* @return The hash of the byte range.
*/
function keccak(
bytes memory self,
uint256 offset,
uint256 len
) internal pure returns (bytes32 ret) {
require(offset + len <= self.length);
assembly {
ret := keccak256(add(add(self, 32), offset), len)
}
}
/**
* @dev Returns the ENS namehash of a DNS-encoded name.
* @param self The DNS-encoded name to hash.
* @param offset The offset at which to start hashing.
* @return The namehash of the name.
*/
function namehash(
bytes memory self,
uint256 offset
) internal pure returns (bytes32) {
(bytes32 labelhash, uint256 newOffset) = readLabel(self, offset);
if (labelhash == bytes32(0)) {
require(offset == self.length - 1, "namehash: Junk at end of name");
return bytes32(0);
}
return
keccak256(abi.encodePacked(namehash(self, newOffset), labelhash));
}
/**
* @dev Returns the keccak-256 hash of a DNS-encoded label, and the offset to the start of the next label.
* @param self The byte string to read a label from.
* @param idx The index to read a label at.
* @return labelhash The hash of the label at the specified index, or 0 if it is the last label.
* @return newIdx The index of the start of the next label.
*/
function readLabel(
bytes memory self,
uint256 idx
) internal pure returns (bytes32 labelhash, uint256 newIdx) {
require(idx < self.length, "readLabel: Index out of bounds");
uint256 len = uint256(uint8(self[idx]));
if (len > 0) {
labelhash = keccak(self, idx + 1, len);
} else {
labelhash = bytes32(0);
}
newIdx = idx + len + 1;
}
/*
* @dev Returns a positive number if `other` comes lexicographically after
* `self`, a negative number if it comes before, or zero if the
* contents of the two bytes are equal.
* @param self The first bytes to compare.
* @param other The second bytes to compare.
* @return The result of the comparison.
*/
function compare(
bytes memory self,
bytes memory other
) internal pure returns (int256) {
return compare(self, 0, self.length, other, 0, other.length);
}
/*
* @dev Returns a positive number if `other` comes lexicographically after
* `self`, a negative number if it comes before, or zero if the
* contents of the two bytes are equal. Comparison is done per-rune,
* on unicode codepoints.
* @param self The first bytes to compare.
* @param offset The offset of self.
* @param len The length of self.
* @param other The second bytes to compare.
* @param otheroffset The offset of the other string.
* @param otherlen The length of the other string.
* @return The result of the comparison.
*/
function compare(
bytes memory self,
uint256 offset,
uint256 len,
bytes memory other,
uint256 otheroffset,
uint256 otherlen
) internal pure returns (int256) {
if (offset + len > self.length) {
revert OffsetOutOfBoundsError(offset + len, self.length);
}
if (otheroffset + otherlen > other.length) {
revert OffsetOutOfBoundsError(otheroffset + otherlen, other.length);
}
uint256 shortest = len;
if (otherlen < len) shortest = otherlen;
uint256 selfptr;
uint256 otherptr;
assembly {
selfptr := add(self, add(offset, 32))
otherptr := add(other, add(otheroffset, 32))
}
for (uint256 idx = 0; idx < shortest; idx += 32) {
uint256 a;
uint256 b;
assembly {
a := mload(selfptr)
b := mload(otherptr)
}
if (a != b) {
// Mask out irrelevant bytes and check again
uint256 mask;
if (shortest - idx >= 32) {
mask = type(uint256).max;
} else {
mask = ~(2 ** (8 * (idx + 32 - shortest)) - 1);
}
int256 diff = int256(a & mask) - int256(b & mask);
if (diff != 0) return diff;
}
selfptr += 32;
otherptr += 32;
}
return int256(len) - int256(otherlen);
}
/*
* @dev Returns true if the two byte ranges are equal.
* @param self The first byte range to compare.
* @param offset The offset into the first byte range.
* @param other The second byte range to compare.
* @param otherOffset The offset into the second byte range.
* @param len The number of bytes to compare
* @return True if the byte ranges are equal, false otherwise.
*/
function equals(
bytes memory self,
uint256 offset,
bytes memory other,
uint256 otherOffset,
uint256 len
) internal pure returns (bool) {
return keccak(self, offset, len) == keccak(other, otherOffset, len);
}
/*
* @dev Returns true if the two byte ranges are equal with offsets.
* @param self The first byte range to compare.
* @param offset The offset into the first byte range.
* @param other The second byte range to compare.
* @param otherOffset The offset into the second byte range.
* @return True if the byte ranges are equal, false otherwise.
*/
function equals(
bytes memory self,
uint256 offset,
bytes memory other,
uint256 otherOffset
) internal pure returns (bool) {
return
keccak(self, offset, self.length - offset) ==
keccak(other, otherOffset, other.length - otherOffset);
}
/*
* @dev Compares a range of 'self' to all of 'other' and returns True iff
* they are equal.
* @param self The first byte range to compare.
* @param offset The offset into the first byte range.
* @param other The second byte range to compare.
* @return True if the byte ranges are equal, false otherwise.
*/
function equals(
bytes memory self,
uint256 offset,
bytes memory other
) internal pure returns (bool) {
return
self.length == offset + other.length &&
equals(self, offset, other, 0, other.length);
}
/*
* @dev Returns true if the two byte ranges are equal.
* @param self The first byte range to compare.
* @param other The second byte range to compare.
* @return True if the byte ranges are equal, false otherwise.
*/
function equals(
bytes memory self,
bytes memory other
) internal pure returns (bool) {
return
self.length == other.length &&
equals(self, 0, other, 0, self.length);
}
/*
* @dev Returns the 8-bit number at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes
* @return The specified 8 bits of the string, interpreted as an integer.
*/
function readUint8(
bytes memory self,
uint256 idx
) internal pure returns (uint8 ret) {
return uint8(self[idx]);
}
/*
* @dev Returns the 16-bit number at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes
* @return The specified 16 bits of the string, interpreted as an integer.
*/
function readUint16(
bytes memory self,
uint256 idx
) internal pure returns (uint16 ret) {
require(idx + 2 <= self.length);
assembly {
ret := and(mload(add(add(self, 2), idx)), 0xFFFF)
}
}
/*
* @dev Returns the 32-bit number at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes
* @return The specified 32 bits of the string, interpreted as an integer.
*/
function readUint32(
bytes memory self,
uint256 idx
) internal pure returns (uint32 ret) {
require(idx + 4 <= self.length);
assembly {
ret := and(mload(add(add(self, 4), idx)), 0xFFFFFFFF)
}
}
/*
* @dev Returns the 32 byte value at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes
* @return The specified 32 bytes of the string.
*/
function readBytes32(
bytes memory self,
uint256 idx
) internal pure returns (bytes32 ret) {
require(idx + 32 <= self.length);
assembly {
ret := mload(add(add(self, 32), idx))
}
}
/*
* @dev Returns the 32 byte value at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes
* @return The specified 32 bytes of the string.
*/
function readBytes20(
bytes memory self,
uint256 idx
) internal pure returns (bytes20 ret) {
require(idx + 20 <= self.length);
assembly {
ret := and(
mload(add(add(self, 32), idx)),
0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF000000000000000000000000
)
}
}
/*
* @dev Returns the n byte value at the specified index of self.
* @param self The byte string.
* @param idx The index into the bytes.
* @param len The number of bytes.
* @return The specified 32 bytes of the string.
*/
function readBytesN(
bytes memory self,
uint256 idx,
uint256 len
) internal pure returns (bytes32 ret) {
require(len <= 32);
require(idx + len <= self.length);
assembly {
let mask := not(sub(exp(256, sub(32, len)), 1))
ret := and(mload(add(add(self, 32), idx)), mask)
}
}
function memcpy(uint256 dest, uint256 src, uint256 len) private pure {
// Copy word-length chunks while possible
for (; len >= 32; len -= 32) {
assembly {
mstore(dest, mload(src))
}
dest += 32;
src += 32;
}
// Copy remaining bytes
unchecked {
uint256 mask = (256 ** (32 - len)) - 1;
assembly {
let srcpart := and(mload(src), not(mask))
let destpart := and(mload(dest), mask)
mstore(dest, or(destpart, srcpart))
}
}
}
/*
* @dev Copies a substring into a new byte string.
* @param self The byte string to copy from.
* @param offset The offset to start copying at.
* @param len The number of bytes to copy.
*/
function substring(
bytes memory self,
uint256 offset,
uint256 len
) internal pure returns (bytes memory) {
require(offset + len <= self.length);
bytes memory ret = new bytes(len);
uint256 dest;
uint256 src;
assembly {
dest := add(ret, 32)
src := add(add(self, 32), offset)
}
memcpy(dest, src, len);
return ret;
}
// Maps characters from 0x30 to 0x7A to their base32 values.
// 0xFF represents invalid characters in that range.
bytes constant base32HexTable =
hex"00010203040506070809FFFFFFFFFFFFFF0A0B0C0D0E0F101112131415161718191A1B1C1D1E1FFFFFFFFFFFFFFFFFFFFF0A0B0C0D0E0F101112131415161718191A1B1C1D1E1F";
/**
* @dev Decodes unpadded base32 data of up to one word in length.
* @param self The data to decode.
* @param off Offset into the string to start at.
* @param len Number of characters to decode.
* @return The decoded data, left aligned.
*/
function base32HexDecodeWord(
bytes memory self,
uint256 off,
uint256 len
) internal pure returns (bytes32) {
require(len <= 52);
uint256 ret = 0;
uint8 decoded;
for (uint256 i = 0; i < len; i++) {
bytes1 char = self[off + i];
require(char >= 0x30 && char <= 0x7A);
decoded = uint8(base32HexTable[uint256(uint8(char)) - 0x30]);
require(decoded <= 0x20);
if (i == len - 1) {
break;
}
ret = (ret << 5) | decoded;
}
uint256 bitlen = len * 5;
if (len % 8 == 0) {
// Multiple of 8 characters, no padding
ret = (ret << 5) | decoded;
} else if (len % 8 == 2) {
// Two extra characters - 1 byte
ret = (ret << 3) | (decoded >> 2);
bitlen -= 2;
} else if (len % 8 == 4) {
// Four extra characters - 2 bytes
ret = (ret << 1) | (decoded >> 4);
bitlen -= 4;
} else if (len % 8 == 5) {
// Five extra characters - 3 bytes
ret = (ret << 4) | (decoded >> 1);
bitlen -= 1;
} else if (len % 8 == 7) {
// Seven extra characters - 4 bytes
ret = (ret << 2) | (decoded >> 3);
bitlen -= 3;
} else {
revert();
}
return bytes32(ret << (256 - bitlen));
}
/**
* @dev Finds the first occurrence of the byte `needle` in `self`.
* @param self The string to search
* @param off The offset to start searching at
* @param len The number of bytes to search
* @param needle The byte to search for
* @return The offset of `needle` in `self`, or 2**256-1 if it was not found.
*/
function find(
bytes memory self,
uint256 off,
uint256 len,
bytes1 needle
) internal pure returns (uint256) {
for (uint256 idx = off; idx < off + len; idx++) {
if (self[idx] == needle) {
return idx;
}
}
return type(uint256).max;
}
}//SPDX-License-Identifier: MIT
pragma solidity ~0.8.17;
interface IMetadataService {
function uri(uint256) external view returns (string memory);
}//SPDX-License-Identifier: MIT
pragma solidity ~0.8.17;
import "../registry/ENS.sol";
import "../ethregistrar/IBaseRegistrar.sol";
import "@openzeppelin/contracts/token/ERC1155/IERC1155.sol";
import "./IMetadataService.sol";
import "./INameWrapperUpgrade.sol";
uint32 constant CANNOT_UNWRAP = 1;
uint32 constant CANNOT_BURN_FUSES = 2;
uint32 constant CANNOT_TRANSFER = 4;
uint32 constant CANNOT_SET_RESOLVER = 8;
uint32 constant CANNOT_SET_TTL = 16;
uint32 constant CANNOT_CREATE_SUBDOMAIN = 32;
uint32 constant CANNOT_APPROVE = 64;
//uint16 reserved for parent controlled fuses from bit 17 to bit 32
uint32 constant PARENT_CANNOT_CONTROL = 1 << 16;
uint32 constant IS_DOT_ETH = 1 << 17;
uint32 constant CAN_EXTEND_EXPIRY = 1 << 18;
uint32 constant CAN_DO_EVERYTHING = 0;
uint32 constant PARENT_CONTROLLED_FUSES = 0xFFFF0000;
// all fuses apart from IS_DOT_ETH
uint32 constant USER_SETTABLE_FUSES = 0xFFFDFFFF;
interface INameWrapper is IERC1155 {
event NameWrapped(
bytes32 indexed node,
bytes name,
address owner,
uint32 fuses,
uint64 expiry
);
event NameUnwrapped(bytes32 indexed node, address owner);
event FusesSet(bytes32 indexed node, uint32 fuses);
event ExpiryExtended(bytes32 indexed node, uint64 expiry);
function ens() external view returns (ENS);
function registrar() external view returns (IBaseRegistrar);
function metadataService() external view returns (IMetadataService);
function names(bytes32) external view returns (bytes memory);
function name() external view returns (string memory);
function upgradeContract() external view returns (INameWrapperUpgrade);
function supportsInterface(bytes4 interfaceID) external view returns (bool);
function wrap(
bytes calldata name,
address wrappedOwner,
address resolver
) external;
function wrapETH2LD(
string calldata label,
address wrappedOwner,
uint16 ownerControlledFuses,
address resolver
) external returns (uint64 expires);
function registerAndWrapETH2LD(
string calldata label,
address wrappedOwner,
uint256 duration,
address resolver,
uint16 ownerControlledFuses
) external returns (uint256 registrarExpiry);
function renew(
uint256 labelHash,
uint256 duration
) external returns (uint256 expires);
function unwrap(bytes32 node, bytes32 label, address owner) external;
function unwrapETH2LD(
bytes32 label,
address newRegistrant,
address newController
) external;
function upgrade(bytes calldata name, bytes calldata extraData) external;
function setFuses(
bytes32 node,
uint16 ownerControlledFuses
) external returns (uint32 newFuses);
function setChildFuses(
bytes32 parentNode,
bytes32 labelhash,
uint32 fuses,
uint64 expiry
) external;
function setSubnodeRecord(
bytes32 node,
string calldata label,
address owner,
address resolver,
uint64 ttl,
uint32 fuses,
uint64 expiry
) external returns (bytes32);
function setRecord(
bytes32 node,
address owner,
address resolver,
uint64 ttl
) external;
function setSubnodeOwner(
bytes32 node,
string calldata label,
address newOwner,
uint32 fuses,
uint64 expiry
) external returns (bytes32);
function extendExpiry(
bytes32 node,
bytes32 labelhash,
uint64 expiry
) external returns (uint64);
function canModifyName(
bytes32 node,
address addr
) external view returns (bool);
function setResolver(bytes32 node, address resolver) external;
function setTTL(bytes32 node, uint64 ttl) external;
function ownerOf(uint256 id) external view returns (address owner);
function approve(address to, uint256 tokenId) external;
function getApproved(uint256 tokenId) external view returns (address);
function getData(
uint256 id
) external view returns (address, uint32, uint64);
function setMetadataService(IMetadataService _metadataService) external;
function uri(uint256 tokenId) external view returns (string memory);
function setUpgradeContract(INameWrapperUpgrade _upgradeAddress) external;
function allFusesBurned(
bytes32 node,
uint32 fuseMask
) external view returns (bool);
function isWrapped(bytes32) external view returns (bool);
function isWrapped(bytes32, bytes32) external view returns (bool);
}//SPDX-License-Identifier: MIT
pragma solidity ~0.8.17;
interface INameWrapperUpgrade {
function wrapFromUpgrade(
bytes calldata name,
address wrappedOwner,
uint32 fuses,
uint64 expiry,
address approved,
bytes calldata extraData
) external;
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (access/Ownable.sol)
pragma solidity ^0.8.20;
import {Context} from "../utils/Context.sol";
/**
* @dev Contract module which provides a basic access control mechanism, where
* there is an account (an owner) that can be granted exclusive access to
* specific functions.
*
* The initial owner is set to the address provided by the deployer. This can
* later be changed with {transferOwnership}.
*
* This module is used through inheritance. It will make available the modifier
* `onlyOwner`, which can be applied to your functions to restrict their use to
* the owner.
*/
abstract contract Ownable is Context {
address private _owner;
/**
* @dev The caller account is not authorized to perform an operation.
*/
error OwnableUnauthorizedAccount(address account);
/**
* @dev The owner is not a valid owner account. (eg. `address(0)`)
*/
error OwnableInvalidOwner(address owner);
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
/**
* @dev Initializes the contract setting the address provided by the deployer as the initial owner.
*/
constructor(address initialOwner) {
if (initialOwner == address(0)) {
revert OwnableInvalidOwner(address(0));
}
_transferOwnership(initialOwner);
}
/**
* @dev Throws if called by any account other than the owner.
*/
modifier onlyOwner() {
_checkOwner();
_;
}
/**
* @dev Returns the address of the current owner.
*/
function owner() public view virtual returns (address) {
return _owner;
}
/**
* @dev Throws if the sender is not the owner.
*/
function _checkOwner() internal view virtual {
if (owner() != _msgSender()) {
revert OwnableUnauthorizedAccount(_msgSender());
}
}
/**
* @dev Leaves the contract without owner. It will not be possible to call
* `onlyOwner` functions. Can only be called by the current owner.
*
* NOTE: Renouncing ownership will leave the contract without an owner,
* thereby disabling any functionality that is only available to the owner.
*/
function renounceOwnership() public virtual onlyOwner {
_transferOwnership(address(0));
}
/**
* @dev Transfers ownership of the contract to a new account (`newOwner`).
* Can only be called by the current owner.
*/
function transferOwnership(address newOwner) public virtual onlyOwner {
if (newOwner == address(0)) {
revert OwnableInvalidOwner(address(0));
}
_transferOwnership(newOwner);
}
/**
* @dev Transfers ownership of the contract to a new account (`newOwner`).
* Internal function without access restriction.
*/
function _transferOwnership(address newOwner) internal virtual {
address oldOwner = _owner;
_owner = newOwner;
emit OwnershipTransferred(oldOwner, newOwner);
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.1) (token/ERC1155/IERC1155.sol)
pragma solidity ^0.8.20;
import {IERC165} from "../../utils/introspection/IERC165.sol";
/**
* @dev Required interface of an ERC1155 compliant contract, as defined in the
* https://eips.ethereum.org/EIPS/eip-1155[EIP].
*/
interface IERC1155 is IERC165 {
/**
* @dev Emitted when `value` amount of tokens of type `id` are transferred from `from` to `to` by `operator`.
*/
event TransferSingle(address indexed operator, address indexed from, address indexed to, uint256 id, uint256 value);
/**
* @dev Equivalent to multiple {TransferSingle} events, where `operator`, `from` and `to` are the same for all
* transfers.
*/
event TransferBatch(
address indexed operator,
address indexed from,
address indexed to,
uint256[] ids,
uint256[] values
);
/**
* @dev Emitted when `account` grants or revokes permission to `operator` to transfer their tokens, according to
* `approved`.
*/
event ApprovalForAll(address indexed account, address indexed operator, bool approved);
/**
* @dev Emitted when the URI for token type `id` changes to `value`, if it is a non-programmatic URI.
*
* If an {URI} event was emitted for `id`, the standard
* https://eips.ethereum.org/EIPS/eip-1155#metadata-extensions[guarantees] that `value` will equal the value
* returned by {IERC1155MetadataURI-uri}.
*/
event URI(string value, uint256 indexed id);
/**
* @dev Returns the value of tokens of token type `id` owned by `account`.
*
* Requirements:
*
* - `account` cannot be the zero address.
*/
function balanceOf(address account, uint256 id) external view returns (uint256);
/**
* @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {balanceOf}.
*
* Requirements:
*
* - `accounts` and `ids` must have the same length.
*/
function balanceOfBatch(
address[] calldata accounts,
uint256[] calldata ids
) external view returns (uint256[] memory);
/**
* @dev Grants or revokes permission to `operator` to transfer the caller's tokens, according to `approved`,
*
* Emits an {ApprovalForAll} event.
*
* Requirements:
*
* - `operator` cannot be the caller.
*/
function setApprovalForAll(address operator, bool approved) external;
/**
* @dev Returns true if `operator` is approved to transfer ``account``'s tokens.
*
* See {setApprovalForAll}.
*/
function isApprovedForAll(address account, address operator) external view returns (bool);
/**
* @dev Transfers a `value` amount of tokens of type `id` from `from` to `to`.
*
* WARNING: This function can potentially allow a reentrancy attack when transferring tokens
* to an untrusted contract, when invoking {onERC1155Received} on the receiver.
* Ensure to follow the checks-effects-interactions pattern and consider employing
* reentrancy guards when interacting with untrusted contracts.
*
* Emits a {TransferSingle} event.
*
* Requirements:
*
* - `to` cannot be the zero address.
* - If the caller is not `from`, it must have been approved to spend ``from``'s tokens via {setApprovalForAll}.
* - `from` must have a balance of tokens of type `id` of at least `value` amount.
* - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the
* acceptance magic value.
*/
function safeTransferFrom(address from, address to, uint256 id, uint256 value, bytes calldata data) external;
/**
* @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {safeTransferFrom}.
*
* WARNING: This function can potentially allow a reentrancy attack when transferring tokens
* to an untrusted contract, when invoking {onERC1155BatchReceived} on the receiver.
* Ensure to follow the checks-effects-interactions pattern and consider employing
* reentrancy guards when interacting with untrusted contracts.
*
* Emits either a {TransferSingle} or a {TransferBatch} event, depending on the length of the array arguments.
*
* Requirements:
*
* - `ids` and `values` must have the same length.
* - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the
* acceptance magic value.
*/
function safeBatchTransferFrom(
address from,
address to,
uint256[] calldata ids,
uint256[] calldata values,
bytes calldata data
) external;
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (token/ERC721/IERC721.sol)
pragma solidity ^0.8.20;
import {IERC165} from "../../utils/introspection/IERC165.sol";
/**
* @dev Required interface of an ERC721 compliant contract.
*/
interface IERC721 is IERC165 {
/**
* @dev Emitted when `tokenId` token is transferred from `from` to `to`.
*/
event Transfer(address indexed from, address indexed to, uint256 indexed tokenId);
/**
* @dev Emitted when `owner` enables `approved` to manage the `tokenId` token.
*/
event Approval(address indexed owner, address indexed approved, uint256 indexed tokenId);
/**
* @dev Emitted when `owner` enables or disables (`approved`) `operator` to manage all of its assets.
*/
event ApprovalForAll(address indexed owner, address indexed operator, bool approved);
/**
* @dev Returns the number of tokens in ``owner``'s account.
*/
function balanceOf(address owner) external view returns (uint256 balance);
/**
* @dev Returns the owner of the `tokenId` token.
*
* Requirements:
*
* - `tokenId` must exist.
*/
function ownerOf(uint256 tokenId) external view returns (address owner);
/**
* @dev Safely transfers `tokenId` token from `from` to `to`.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must exist and be owned by `from`.
* - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}.
* - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon
* a safe transfer.
*
* Emits a {Transfer} event.
*/
function safeTransferFrom(address from, address to, uint256 tokenId, bytes calldata data) external;
/**
* @dev Safely transfers `tokenId` token from `from` to `to`, checking first that contract recipients
* are aware of the ERC721 protocol to prevent tokens from being forever locked.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must exist and be owned by `from`.
* - If the caller is not `from`, it must have been allowed to move this token by either {approve} or
* {setApprovalForAll}.
* - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon
* a safe transfer.
*
* Emits a {Transfer} event.
*/
function safeTransferFrom(address from, address to, uint256 tokenId) external;
/**
* @dev Transfers `tokenId` token from `from` to `to`.
*
* WARNING: Note that the caller is responsible to confirm that the recipient is capable of receiving ERC721
* or else they may be permanently lost. Usage of {safeTransferFrom} prevents loss, though the caller must
* understand this adds an external call which potentially creates a reentrancy vulnerability.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must be owned by `from`.
* - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}.
*
* Emits a {Transfer} event.
*/
function transferFrom(address from, address to, uint256 tokenId) external;
/**
* @dev Gives permission to `to` to transfer `tokenId` token to another account.
* The approval is cleared when the token is transferred.
*
* Only a single account can be approved at a time, so approving the zero address clears previous approvals.
*
* Requirements:
*
* - The caller must own the token or be an approved operator.
* - `tokenId` must exist.
*
* Emits an {Approval} event.
*/
function approve(address to, uint256 tokenId) external;
/**
* @dev Approve or remove `operator` as an operator for the caller.
* Operators can call {transferFrom} or {safeTransferFrom} for any token owned by the caller.
*
* Requirements:
*
* - The `operator` cannot be the address zero.
*
* Emits an {ApprovalForAll} event.
*/
function setApprovalForAll(address operator, bool approved) external;
/**
* @dev Returns the account approved for `tokenId` token.
*
* Requirements:
*
* - `tokenId` must exist.
*/
function getApproved(uint256 tokenId) external view returns (address operator);
/**
* @dev Returns if the `operator` is allowed to manage all of the assets of `owner`.
*
* See {setApprovalForAll}
*/
function isApprovedForAll(address owner, address operator) external view returns (bool);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.1) (utils/Context.sol)
pragma solidity ^0.8.20;
/**
* @dev Provides information about the current execution context, including the
* sender of the transaction and its data. While these are generally available
* via msg.sender and msg.data, they should not be accessed in such a direct
* manner, since when dealing with meta-transactions the account sending and
* paying for execution may not be the actual sender (as far as an application
* is concerned).
*
* This contract is only required for intermediate, library-like contracts.
*/
abstract contract Context {
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
function _contextSuffixLength() internal view virtual returns (uint256) {
return 0;
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/cryptography/ECDSA.sol)
pragma solidity ^0.8.20;
/**
* @dev Elliptic Curve Digital Signature Algorithm (ECDSA) operations.
*
* These functions can be used to verify that a message was signed by the holder
* of the private keys of a given address.
*/
library ECDSA {
enum RecoverError {
NoError,
InvalidSignature,
InvalidSignatureLength,
InvalidSignatureS
}
/**
* @dev The signature derives the `address(0)`.
*/
error ECDSAInvalidSignature();
/**
* @dev The signature has an invalid length.
*/
error ECDSAInvalidSignatureLength(uint256 length);
/**
* @dev The signature has an S value that is in the upper half order.
*/
error ECDSAInvalidSignatureS(bytes32 s);
/**
* @dev Returns the address that signed a hashed message (`hash`) with `signature` or an error. This will not
* return address(0) without also returning an error description. Errors are documented using an enum (error type)
* and a bytes32 providing additional information about the error.
*
* If no error is returned, then the address can be used for verification purposes.
*
* The `ecrecover` EVM precompile allows for malleable (non-unique) signatures:
* this function rejects them by requiring the `s` value to be in the lower
* half order, and the `v` value to be either 27 or 28.
*
* IMPORTANT: `hash` _must_ be the result of a hash operation for the
* verification to be secure: it is possible to craft signatures that
* recover to arbitrary addresses for non-hashed data. A safe way to ensure
* this is by receiving a hash of the original message (which may otherwise
* be too long), and then calling {MessageHashUtils-toEthSignedMessageHash} on it.
*
* Documentation for signature generation:
* - with https://web3js.readthedocs.io/en/v1.3.4/web3-eth-accounts.html#sign[Web3.js]
* - with https://docs.ethers.io/v5/api/signer/#Signer-signMessage[ethers]
*/
function tryRecover(bytes32 hash, bytes memory signature) internal pure returns (address, RecoverError, bytes32) {
if (signature.length == 65) {
bytes32 r;
bytes32 s;
uint8 v;
// ecrecover takes the signature parameters, and the only way to get them
// currently is to use assembly.
/// @solidity memory-safe-assembly
assembly {
r := mload(add(signature, 0x20))
s := mload(add(signature, 0x40))
v := byte(0, mload(add(signature, 0x60)))
}
return tryRecover(hash, v, r, s);
} else {
return (address(0), RecoverError.InvalidSignatureLength, bytes32(signature.length));
}
}
/**
* @dev Returns the address that signed a hashed message (`hash`) with
* `signature`. This address can then be used for verification purposes.
*
* The `ecrecover` EVM precompile allows for malleable (non-unique) signatures:
* this function rejects them by requiring the `s` value to be in the lower
* half order, and the `v` value to be either 27 or 28.
*
* IMPORTANT: `hash` _must_ be the result of a hash operation for the
* verification to be secure: it is possible to craft signatures that
* recover to arbitrary addresses for non-hashed data. A safe way to ensure
* this is by receiving a hash of the original message (which may otherwise
* be too long), and then calling {MessageHashUtils-toEthSignedMessageHash} on it.
*/
function recover(bytes32 hash, bytes memory signature) internal pure returns (address) {
(address recovered, RecoverError error, bytes32 errorArg) = tryRecover(hash, signature);
_throwError(error, errorArg);
return recovered;
}
/**
* @dev Overload of {ECDSA-tryRecover} that receives the `r` and `vs` short-signature fields separately.
*
* See https://eips.ethereum.org/EIPS/eip-2098[EIP-2098 short signatures]
*/
function tryRecover(bytes32 hash, bytes32 r, bytes32 vs) internal pure returns (address, RecoverError, bytes32) {
unchecked {
bytes32 s = vs & bytes32(0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff);
// We do not check for an overflow here since the shift operation results in 0 or 1.
uint8 v = uint8((uint256(vs) >> 255) + 27);
return tryRecover(hash, v, r, s);
}
}
/**
* @dev Overload of {ECDSA-recover} that receives the `r and `vs` short-signature fields separately.
*/
function recover(bytes32 hash, bytes32 r, bytes32 vs) internal pure returns (address) {
(address recovered, RecoverError error, bytes32 errorArg) = tryRecover(hash, r, vs);
_throwError(error, errorArg);
return recovered;
}
/**
* @dev Overload of {ECDSA-tryRecover} that receives the `v`,
* `r` and `s` signature fields separately.
*/
function tryRecover(
bytes32 hash,
uint8 v,
bytes32 r,
bytes32 s
) internal pure returns (address, RecoverError, bytes32) {
// EIP-2 still allows signature malleability for ecrecover(). Remove this possibility and make the signature
// unique. Appendix F in the Ethereum Yellow paper (https://ethereum.github.io/yellowpaper/paper.pdf), defines
// the valid range for s in (301): 0 < s < secp256k1n ÷ 2 + 1, and for v in (302): v ∈ {27, 28}. Most
// signatures from current libraries generate a unique signature with an s-value in the lower half order.
//
// If your library generates malleable signatures, such as s-values in the upper range, calculate a new s-value
// with 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - s1 and flip v from 27 to 28 or
// vice versa. If your library also generates signatures with 0/1 for v instead 27/28, add 27 to v to accept
// these malleable signatures as well.
if (uint256(s) > 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0) {
return (address(0), RecoverError.InvalidSignatureS, s);
}
// If the signature is valid (and not malleable), return the signer address
address signer = ecrecover(hash, v, r, s);
if (signer == address(0)) {
return (address(0), RecoverError.InvalidSignature, bytes32(0));
}
return (signer, RecoverError.NoError, bytes32(0));
}
/**
* @dev Overload of {ECDSA-recover} that receives the `v`,
* `r` and `s` signature fields separately.
*/
function recover(bytes32 hash, uint8 v, bytes32 r, bytes32 s) internal pure returns (address) {
(address recovered, RecoverError error, bytes32 errorArg) = tryRecover(hash, v, r, s);
_throwError(error, errorArg);
return recovered;
}
/**
* @dev Optionally reverts with the corresponding custom error according to the `error` argument provided.
*/
function _throwError(RecoverError error, bytes32 errorArg) private pure {
if (error == RecoverError.NoError) {
return; // no error: do nothing
} else if (error == RecoverError.InvalidSignature) {
revert ECDSAInvalidSignature();
} else if (error == RecoverError.InvalidSignatureLength) {
revert ECDSAInvalidSignatureLength(uint256(errorArg));
} else if (error == RecoverError.InvalidSignatureS) {
revert ECDSAInvalidSignatureS(errorArg);
}
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/introspection/ERC165.sol)
pragma solidity ^0.8.20;
import {IERC165} from "./IERC165.sol";
/**
* @dev Implementation of the {IERC165} interface.
*
* Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check
* for the additional interface id that will be supported. For example:
*
* ```solidity
* function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
* return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId);
* }
* ```
*/
abstract contract ERC165 is IERC165 {
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(bytes4 interfaceId) public view virtual returns (bool) {
return interfaceId == type(IERC165).interfaceId;
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/introspection/IERC165.sol)
pragma solidity ^0.8.20;
/**
* @dev Interface of the ERC165 standard, as defined in the
* https://eips.ethereum.org/EIPS/eip-165[EIP].
*
* Implementers can declare support of contract interfaces, which can then be
* queried by others ({ERC165Checker}).
*
* For an implementation, see {ERC165}.
*/
interface IERC165 {
/**
* @dev Returns true if this contract implements the interface defined by
* `interfaceId`. See the corresponding
* https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]
* to learn more about how these ids are created.
*
* This function call must use less than 30 000 gas.
*/
function supportsInterface(bytes4 interfaceId) external view returns (bool);
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/IExtendedResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/ABIResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/AddrResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/ContentHashResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/NameResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/TextResolver.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/Multicallable.sol";
import "@ensdomains/ens-contracts/contracts/resolvers/profiles/InterfaceResolver.sol";
import {ENS} from "@ensdomains/ens-contracts/contracts/registry/ENS.sol";
import {INameWrapper} from "@ensdomains/ens-contracts/contracts/wrapper/INameWrapper.sol";
import {Ownable} from "@openzeppelin/contracts/access/Ownable.sol";
abstract contract EnsResolverBase is
Multicallable,
ABIResolver,
AddrResolver,
ContentHashResolver,
InterfaceResolver,
NameResolver,
TextResolver,
Ownable
{
ENS immutable ens;
INameWrapper immutable nameWrapper;
constructor(address _ENS, address _nameWrapper) {
ens = ENS(_ENS);
nameWrapper = INameWrapper(_nameWrapper);
}
function isAuthorised(bytes32 node) internal view override returns (bool) {
return hasNamePermissions(node);
}
function hasNamePermissions(bytes32 node) internal view returns (bool) {
return
ens.owner(node) == _msgSender() ||
nameWrapper.canModifyName(node, _msgSender());
}
modifier isNodeOwner(bytes32 node) {
require(hasNamePermissions(node), "No permissions to modify name");
_;
}
function resolve(
bytes memory dnsName,
bytes memory data
) public view virtual returns (bytes memory);
function supportsInterface(
bytes4 interfaceId
)
public
view
override(
Multicallable,
ABIResolver,
AddrResolver,
ContentHashResolver,
InterfaceResolver,
NameResolver,
TextResolver
)
returns (bool)
{
return
interfaceId == type(IExtendedResolver).interfaceId ||
super.supportsInterface(interfaceId);
}
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
import "@openzeppelin/contracts/utils/cryptography/ECDSA.sol";
import {Ownable} from "@openzeppelin/contracts/access/Ownable.sol";
interface IResolverService {
function resolve(
bytes calldata name,
bytes calldata data
)
external
view
returns (bytes memory result, uint64 expires, bytes memory sig);
}
abstract contract OffchainResolver is Ownable {
mapping(address => bool) private signers;
event SignerChanged(address signer, bool removed);
event OffchainUrlsChanged(string[] urls);
error OffchainLookup(
address sender,
string[] urls,
bytes callData,
bytes4 callbackFunction,
bytes extraData
);
constructor(address[] memory _signers) {
modifyOffchainSigners(_signers, false);
}
/**
* Resolves a name, as specified by ENSIP 10.
* @param name The DNS-encoded name to resolve.
* @param data The ABI encoded data for the underlying resolution function (Eg, addr(bytes32), text(bytes32,string), etc).
* @return The return data, ABI encoded identically to the underlying function.
*/
function _resolveOffchain(
bytes memory name,
bytes memory data,
string[] memory urls
) internal view returns (bytes memory) {
bytes memory callData = abi.encodeWithSelector(
IResolverService.resolve.selector,
name,
data
);
revert OffchainLookup(
address(this),
urls,
callData,
OffchainResolver.resolveWithProof.selector,
abi.encode(callData, address(this))
);
}
/**
* Callback used by CCIP read compatible clients to verify and parse the response.
*/
function resolveWithProof(
bytes calldata response,
bytes calldata extraData
) external view returns (bytes memory) {
(address signer, bytes memory result) = verify(
extraData,
response
);
require(signers[signer], "Signature: Invalid signature");
return result;
}
/**
* @dev Generates a hash for signing/verifying.
* @param target: The address the signature is for.
* @param request: The original request that was sent.
* @param result: The `result` field of the response (not including the signature part).
*/
function makeSignatureHash(
address target,
uint64 expires,
bytes memory request,
bytes memory result
) internal pure returns (bytes32) {
return
keccak256(
abi.encodePacked(
hex"1900",
target,
expires,
keccak256(request),
keccak256(result)
)
);
}
/**
* @dev Verifies a signed message returned from a callback.
* @param request: The original request that was sent.
* @param response: An ABI encoded tuple of `(bytes result, uint64 expires, bytes sig)`, where `result` is the data to return
* to the caller, and `sig` is the (r,s,v) encoded message signature.
* @return signer: The address that signed this message.
* @return result: The `result` decoded from `response`.
*/
function verify(
bytes calldata request,
bytes calldata response
) internal view returns (address, bytes memory) {
(bytes memory result, uint64 expires, bytes memory sig) = abi.decode(
response,
(bytes, uint64, bytes)
);
(bytes memory extraData, address sender) = abi.decode(
request,
(bytes, address)
);
address signer = ECDSA.recover(
makeSignatureHash(sender, expires, extraData, result),
sig
);
require(
expires >= block.timestamp,
"SignatureVerifier: Signature expired"
);
return (signer, result);
}
function modifyOffchainSigners(
address[] memory _signers,
bool remove
) public onlyOwner {
for (uint i = 0; i < _signers.length; i++) {
if (remove) {
signers[_signers[i]] = false;
emit SignerChanged(_signers[i], true);
} else {
signers[_signers[i]] = true;
emit SignerChanged(_signers[i], false);
}
}
}
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
uint constant OFFCHAIN_DB_RESOLUTION = 9999;
uint constant BASE_RESOLUTION = 8453;
uint constant OP_RESOLUTION = 10;
struct ResolutionConfig {
bool resolveOffchain;
uint resolutionType;
}
struct ResolutionUrls {
uint resolutionType;
string[] urls;
}
interface ITrustlessResolver {
function resolve(
bytes memory dnsName,
bytes memory data,
uint chainId
) external view returns (bytes memory);
}{
"optimizer": {
"enabled": true,
"runs": 200
},
"viaIR": true,
"evmVersion": "paris",
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
},
"libraries": {}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"address[]","name":"_signers","type":"address[]"},{"internalType":"address","name":"ens","type":"address"},{"internalType":"address","name":"nameWrapper","type":"address"},{"internalType":"address","name":"_fallbackResolver","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ECDSAInvalidSignature","type":"error"},{"inputs":[{"internalType":"uint256","name":"length","type":"uint256"}],"name":"ECDSAInvalidSignatureLength","type":"error"},{"inputs":[{"internalType":"bytes32","name":"s","type":"bytes32"}],"name":"ECDSAInvalidSignatureS","type":"error"},{"inputs":[{"internalType":"address","name":"sender","type":"address"},{"internalType":"string[]","name":"urls","type":"string[]"},{"internalType":"bytes","name":"callData","type":"bytes"},{"internalType":"bytes4","name":"callbackFunction","type":"bytes4"},{"internalType":"bytes","name":"extraData","type":"bytes"}],"name":"OffchainLookup","type":"error"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"OwnableInvalidOwner","type":"error"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"OwnableUnauthorizedAccount","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":true,"internalType":"uint256","name":"contentType","type":"uint256"}],"name":"ABIChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"address","name":"a","type":"address"}],"name":"AddrChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"coinType","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"newAddress","type":"bytes"}],"name":"AddressChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"bytes","name":"hash","type":"bytes"}],"name":"ContenthashChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"address","name":"newResolver","type":"address"}],"name":"FallbackResolverSet","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":true,"internalType":"bytes4","name":"interfaceID","type":"bytes4"},{"indexed":false,"internalType":"address","name":"implementer","type":"address"}],"name":"InterfaceChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"string","name":"name","type":"string"}],"name":"NameChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"string[]","name":"urls","type":"string[]"}],"name":"OffchainUrlsChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"prevType","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"newType","type":"uint256"}],"name":"ResolutionConfigChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"resolutionType","type":"uint256"},{"indexed":false,"internalType":"string[]","name":"urls","type":"string[]"}],"name":"ResolutionUrlsChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"signer","type":"address"},{"indexed":false,"internalType":"bool","name":"removed","type":"bool"}],"name":"SignerChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":true,"internalType":"string","name":"indexedKey","type":"string"},{"indexed":false,"internalType":"string","name":"key","type":"string"},{"indexed":false,"internalType":"string","name":"value","type":"string"}],"name":"TextChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"uint64","name":"newVersion","type":"uint64"}],"name":"VersionChanged","type":"event"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint256","name":"contentTypes","type":"uint256"}],"name":"ABI","outputs":[{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"addr","outputs":[{"internalType":"address payable","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint256","name":"coinType","type":"uint256"}],"name":"addr","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"clearRecords","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"name":"configs","outputs":[{"internalType":"bool","name":"resolveOffchain","type":"bool"},{"internalType":"uint256","name":"resolutionType","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"contenthash","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"defaultFallbackResolver","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"name":"fallbackResolvers","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes4","name":"interfaceID","type":"bytes4"}],"name":"interfaceImplementer","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"_signers","type":"address[]"},{"internalType":"bool","name":"remove","type":"bool"}],"name":"modifyOffchainSigners","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes[]","name":"data","type":"bytes[]"}],"name":"multicall","outputs":[{"internalType":"bytes[]","name":"results","type":"bytes[]"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"nodehash","type":"bytes32"},{"internalType":"bytes[]","name":"data","type":"bytes[]"}],"name":"multicallWithNodeCheck","outputs":[{"internalType":"bytes[]","name":"results","type":"bytes[]"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"name":"recordVersions","outputs":[{"internalType":"uint64","name":"","type":"uint64"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"uint256","name":"","type":"uint256"}],"name":"resolutionUrls","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"dnsName","type":"bytes"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"resolve","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"response","type":"bytes"},{"internalType":"bytes","name":"extraData","type":"bytes"}],"name":"resolveWithProof","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint256","name":"contentType","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"setABI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint256","name":"coinType","type":"uint256"},{"internalType":"bytes","name":"a","type":"bytes"}],"name":"setAddr","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"address","name":"a","type":"address"}],"name":"setAddr","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes","name":"hash","type":"bytes"}],"name":"setContenthash","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_fallbackResolver","type":"address"}],"name":"setDefaultFallbackResolver","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"hash","type":"bytes32"},{"internalType":"bool","name":"value","type":"bool"}],"name":"setEmptyResponse","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"address","name":"fallbackResolver","type":"address"}],"name":"setFallbackResolver","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes4","name":"interfaceID","type":"bytes4"},{"internalType":"address","name":"implementer","type":"address"}],"name":"setInterface","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"string","name":"newName","type":"string"}],"name":"setName","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint256","name":"newResolutionType","type":"uint256"}],"name":"setResolutionType","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"resolutionType","type":"uint256"},{"internalType":"string[]","name":"urls","type":"string[]"}],"name":"setResolutionUrls","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"resolutionType","type":"uint256"},{"internalType":"bool","name":"supported","type":"bool"}],"name":"setSupportedResolutionType","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"string","name":"key","type":"string"},{"internalType":"string","name":"value","type":"string"}],"name":"setText","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"string","name":"key","type":"string"}],"name":"text","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"}]Contract Creation Code
604060c0815234620002945762003434803803806200001e81620002af565b928339810190608081830312620002945780516001600160401b039190828111620002945781019280601f850112156200029457835193602093851162000299578460051b90848062000073818501620002af565b809881520192820101928311620002945784809101915b8383106200027957509050620000a391508201620002d5565b90620000bf6060620000b7878401620002d5565b9201620002d5565b933315620002615760078054336001600160a01b031980831682179093556000956001600160a01b03958693909284929183167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e08a80a3166080521660a052835b87835182101562000194575080846200013c60019386620002ea565b5116865260088752888620805460ff1916831790557f70f1a3dba165402559aaa92407aa69ed152f584fde0bc213bcf1c47acef771b68986620001808488620002ea565b51168151908152888a820152a10162000120565b828589896001858b7f290decd9548b62a8d60345a988386fc84ba6bc95484008f6362f93160ef3e5638152600b8452600d8282209460ff199585878254161790557f569e75fc77c1a856f6daaf9e69d8a9566ca34aa47f9133711ce065a571af0cfd8352838320858782541617905561270f835252818120838582541617905561210581528181208385825416179055600a81522091825416179055169060095416176009555161311e9081620003168239608051818181612348015261271a015260a0518161278b0152f35b8551631e4fbdf760e01b815260006004820152602490fd5b81906200028684620002d5565b81520191019084906200008a565b600080fd5b634e487b7160e01b600052604160045260246000fd5b6040519190601f01601f191682016001600160401b038111838210176200029957604052565b51906001600160a01b03821682036200029457565b8051821015620002ff5760209160051b010190565b634e487b7160e01b600052603260045260246000fdfe6080604052600436101561001257600080fd5b60003560e01c806301ffc9a71461024757806310f13a8c14610242578063124a319c1461023d5780632203ab56146102385780632931570214610233578063304e6ade1461022e578063341e9393146102295780633603d758146102245780633b3b57de1461021f57806359d1d43c1461021a578063623195b014610215578063691f343114610210578063715018a61461020b5780637357c5671461020657806377372213146102015780637d85f6e2146101fc5780638b95dd71146101f75780638da5cb5b146101f25780638ed91c46146101ed5780639061b923146101e8578063a4c28248146101e3578063ac9650d8146101de578063aea9467d146101d9578063b9288916146101d4578063bc1c58d1146101cf578063bd47daa3146101ca578063c315b474146101c5578063ce8f6078146101c0578063d5fa2b00146101bb578063d700ff33146101b6578063e32954eb146101b1578063e59d895d146101ac578063f1cb7e06146101a7578063f2fde38b146101a25763f4d4d2f81461019d57600080fd5b6119c6565b611934565b6118d7565b611813565b6116fe565b6116c9565b6115cb565b611591565b61153a565b61139d565b61134e565b61131a565b6112d3565b6111f1565b611046565b610fdb565b610fb2565b610f89565b610e7f565b610dc9565b610ca1565b610c05565b610b45565b610adb565b610a1c565b6109a1565b610972565b6108c5565b6107bc565b61064a565b6105cc565b610584565b6104da565b6103f4565b61027f565b600435906001600160e01b03198216820361026357565b600080fd5b602435906001600160e01b03198216820361026357565b34610263576020366003190112610263576102ca6001600160e01b03196102a461024c565b16639061b92360e01b81149081156102ce575b5060405190151581529081906020820190565b0390f35b631674750f60e21b8114915081156102e8575b50386102b7565b63691f343160e01b811491508115610302575b50386102e1565b6304928c6760e21b81149150811561031c575b50386102fb565b63bc1c58d160e01b811491508115610336575b5038610315565b631d9dabef60e11b8114915081156103b6575b8115610357575b503861032f565b631101d5ab60e11b811491508115610371575b5038610350565b63d700ff3360e01b81149150811561038b575b503861036a565b634fbf043360e01b8114915081156103a5575b5038610384565b6301ffc9a760e01b1490503861039e565b6378e5bf0360e11b81149150610349565b9181601f84011215610263578235916001600160401b038311610263576020838186019501011161026357565b34610263576060366003190112610263576001600160401b03600435602435828111610263576104289036906004016103c7565b604492919235848111610263576104439036906004016103c7565b91909361044f846126f2565b15610263576104d47f448bc014f1536726cf8d54ff3d6481ed3cbc683c2591ca204274009afa09b1a1936000978689528860205260408920541688526006602052604088208689526020526104bd818860408b20602060405180928a8a83378a820190815203019020611b46565b6104c78484611c14565b9660405194859485611c4a565b0390a380f35b346102635760403660031901126102635760206105006104f8610268565b600435611cea565b6040516001600160a01b039091168152f35b919082519283825260005b84811061053e575050826000602080949584010152601f8019910116010190565b60208183018101518483018201520161051d565b90604061056a92603c81528160208201520190610512565b90565b60409061056a939281528160208201520190610512565b34610263576040366003190112610263576105a3602435600435611ed2565b906102ca6040519283928361056d565b8015150361026357565b602435906105ca826105b3565b565b34610263576040366003190112610263576106156024356105ec816105b3565b6105f4612690565b600435600052600d60205260406000209060ff801983541691151516179055565b005b9060406003198301126102635760043591602435906001600160401b03821161026357610646916004016103c7565b9091565b346102635761065836610617565b9091610663816126f2565b1561026357600091818352602093836020526001600160401b03806040862054168552600360205260408520848652602052604085209083116107b7576106b4836106ae835461146a565b83611b01565b8495601f84116001146107295750610706838087987fe379c1624ed7e714cc0937528a32359d69d5281337765313dba4e081b72d757897989161071e575b508160011b916000199060031b1c19161790565b90555b6107186040519283928361200d565b0390a280f35b9050840135386106f2565b601f1984169661073e83600052602060002090565b9187905b89821061079f575050847fe379c1624ed7e714cc0937528a32359d69d5281337765313dba4e081b72d757896979810610785575b5050600183811b019055610709565b830135600019600386901b60f8161c191690553880610776565b80600184958294958901358155019401920190610742565b610ba6565b34610263576040366003190112610263576004356024356107e46107df836126f2565b61201e565b80600052600d60205260ff6040600020541615610874578161086f60016108367ffb370bde575cc90b84f91138780a4144849a157773e7bc467236da4842345e4295600052600c602052604060002090565b01549280600161085085600052600c602052604060002090565b0155604051938493846040919493926060820195825260208201520152565b0390a1005b60405162461bcd60e51b8152602060048201526024808201527f556e737570706f72746564207265736f6c7574696f6e20747970652070726f766044820152631a59195960e21b6064820152608490fd5b34610263576020366003190112610263576004356108e2816126f2565b156102635760009080825281602052604082208054906001600160401b038083169181831461096d577fc6621ccb8f3f5a04bb6502154b2caf6adf5983fe76dfef1cfc9c42e3579db44493826001610718950116906001600160401b03191617905583855284602052604085205416604051918291829190916001600160401b036020820193169052565b61206a565b34610263576020366003190112610263576020610500600435612080565b90602061056a928181520190610512565b3461026357610a06610a0d6102ca6109b836610617565b600094919492808452602095869185835260409586916001600160401b03838320541682526006855282822090825284522083865194859384378201908152030190208251958680926114a4565b0385610bbc565b51928284938452830190610512565b34610263576060366003190112610263576001600160401b0360243560043560443583811161026357610a539036906004016103c7565b610a5c836126f2565b1561026357600019840184811161096d57841661026357610ab491600095848752866020526040872054168652600160205260408620848752602052610aaf856040882090600052602052604060002090565b611f70565b7faa121bbeef5f32f5961a2a28966e769023910fc9479059ee3495d4c1a696efe38380a380f35b346102635760208060031936011261026357610b2a90610b3160406004356000908082528185526001600160401b038383205416825260058552828220908252845220604051938480926114a4565b0383610bbc565b6102ca604051928284938452830190610512565b3461026357600080600319360112610ba357610b5f612690565b600780546001600160a01b0319811690915581906001600160a01b03167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e08280a380f35b80fd5b634e487b7160e01b600052604160045260246000fd5b90601f801991011681019081106001600160401b038211176107b757604052565b6001600160401b0381116107b75760051b60200190565b6001600160a01b0381160361026357565b34610263576040366003190112610263576004356001600160401b038111610263573660238201121561026357806004013590610c4182610bdd565b90610c4f6040519283610bbc565b8282526020926024602084019160051b8301019136831161026357602401905b828210610c885761061584610c826105bd565b906120fb565b8480918335610c9681610bf4565b815201910190610c6f565b3461026357610caf36610617565b9091610cba816126f2565b1561026357600091818352602093836020526001600160401b03806040862054168552600560205260408520848652602052604085209083116107b757610d05836106ae835461146a565b8495601f8411600114610d565750610706838087987fb7d29e911041e8d9b843369e890bcb72c9388692ba48b65ac54e7214c4c348f797989161071e57508160011b916000199060031b1c19161790565b601f19841696610d6b83600052602060002090565b9187905b898210610db1575050847fb7d29e911041e8d9b843369e890bcb72c9388692ba48b65ac54e7214c4c348f796979810610785575050600183811b019055610709565b80600184958294958901358155019401920190610d6f565b3461026357604036600319011261026357610615602435610de9816105b3565b610df1612690565b600435600052600b60205260406000209060ff801983541691151516179055565b6001600160401b0381116107b757601f01601f191660200190565b929192610e3982610e12565b91610e476040519384610bbc565b829481845281830111610263578281602093846000960137010152565b9080601f830112156102635781602061056a93359101610e2d565b34610263576060366003190112610263576001600160401b0360243560043560443583811161026357610eb6903690600401610e64565b90610ec0816126f2565b1561026357610f439281610f3e927f65412581168e88a1e60c6459d7f44ae83ad0832e670826c05a4e2476b57af75260405180610efe88878361056d565b0390a2603c8214610f46575b6000958187528660205260408720541686526002602052604086209086526020526040852090600052602052604060002090565b61224d565b80f35b807f52d7d861f09ab3d26239d492e8968629f95e9e318cf0b73bfddc441522a15fd26020610f7387612810565b6040516001600160a01b039091168152a2610f0a565b34610263576000366003190112610263576007546040516001600160a01b039091168152602090f35b34610263576000366003190112610263576009546040516001600160a01b039091168152602090f35b34610263576040366003190112610263576001600160401b036004358181116102635761100c903690600401610e64565b90602435908111610263576102ca9161102c611032923690600401610e64565b90612316565b604051918291602083526020830190610512565b346102635760403660031901126102635760043560243561106681610bf4565b6110726107df836126f2565b6000828152600a60205260409020546001600160a01b0382811691161461110d57816110ec826110cd7f90e6a2cff4e717c36e6aa27f1da038ed159ffb4bb9a028ac97b4e706c156562795600052600a602052604060002090565b80546001600160a01b0319166001600160a01b03909216919091179055565b604080519182526001600160a01b039092166020820152908190810161086f565b60405162461bcd60e51b815260206004820152602260248201527f53616d652066616c6c6261636b207265736f6c76657220616c72656164792073604482015261195d60f21b6064820152608490fd5b9181601f84011215610263578235916001600160401b038311610263576020808501948460051b01011161026357565b6020808201906020835283518092526040830192602060408460051b8301019501936000915b8483106111c35750505050505090565b90919293949584806111e1600193603f198682030187528a51610512565b98019301930191949392906111b3565b3461026357602080600319360112610263576004356001600160401b0381116102635761122290369060040161115d565b9161122c83610bdd565b9260409161123d6040519586610bbc565b818552601f1961124c83610bdd565b0160005b8181106112c45750505060005b81811061127257604051806102ca878261118d565b806000806112836001948689612b38565b90611292885180938193611adc565b0390305af46112a86112a2611c94565b91611ad5565b6112b28288612239565b526112bd8187612239565b500161125d565b60608782018401528201611250565b34610263576020366003190112610263576004356112f081610bf4565b6112f8612690565b600980546001600160a01b0319166001600160a01b0392909216919091179055005b3461026357602036600319011261026357600435600052600a602052602060018060a01b0360406000205416604051908152f35b346102635760208060031936011261026357610b2a90610b3160406004356000908082528185526001600160401b038383205416825260038552828220908252845220604051938480926114a4565b34610263576040366003190112610263576001600160401b03602480358281116102635736602382011215610263578060040135916113db83610bdd565b926113e96040519485610bbc565b8084526020946024602086019260051b850101933685116102635760248101925b85841061141d57610615876004356123f5565b8335838111610263578201366043820112156102635788916114498392369060448a8201359101610e2d565b81520193019261140a565b634e487b7160e01b600052603260045260246000fd5b90600182811c9216801561149a575b602083101461148457565b634e487b7160e01b600052602260045260246000fd5b91607f1691611479565b8054600093926114b38261146a565b9182825260209360019160018116908160001461151b57506001146114da575b5050505050565b90939495506000929192528360002092846000945b838610611507575050505001019038808080806114d3565b8054858701830152940193859082016114ef565b60ff19168685015250505090151560051b0101915038808080806114d3565b34610263576040366003190112610263576024356000906004358252600e60205260408220805482101561158d5761158691602084611032936102ca96522001604051928380926114a4565b0382610bbc565b8280fd5b3461026357602036600319011261026357600435600052600c602052604080600020600160ff825416910154825191151582526020820152f35b346102635760408060031936011261026357600435906024356115ed81610bf4565b6115f6836126f2565b1561026357611603612c10565b9060601b6020820152611615836126f2565b1561026357610f3e82847f65412581168e88a1e60c6459d7f44ae83ad0832e670826c05a4e2476b57af752610f439551806116508782610552565b0390a2847f52d7d861f09ab3d26239d492e8968629f95e9e318cf0b73bfddc441522a15fd2602061168086612810565b84516001600160a01b039091168152a2600094808652856020526001600160401b038287205416865260026020528186209086526020528420603c600052602052604060002090565b3461026357602036600319011261026357600435600052600060205260206001600160401b0360406000205416604051908152f35b3461026357604080600319360112610263576004356024356001600160401b0381116102635761173290369060040161115d565b61173e81949294610bdd565b9361174c6040519586610bbc565b818552601f1961175b83610bdd565b0160005b8181106118025750508315159360005b83811061178457604051806102ca898261118d565b600190866117d6575b60008061179b838888612b38565b906117aa8a5180938193611adc565b0390305af46117ba6112a2611c94565b6117c4828a612239565b526117cf8189612239565b500161176f565b6117fd836117f76117f16117eb858a8a612b38565b90612b79565b90612b8a565b14612ba7565b61178d565b806060602080938a0101520161175f565b346102635760603660031901126102635760043561182f610268565b906044359061183d82610bf4565b611846816126f2565b15610263577f7c69f06bea0bdef565b709e93a147836b0063ba2dd89f02d0b7e8d931e6a6daa60206000948386528582526001600160401b036040872054168652600482526040862084875282526118b8856110cd8360408a209063ffffffff60e01b16600052602052604060002090565b6040516001600160a01b0390951685526001600160e01b03191693a380f35b346102635760408060031936011261026357610a06906102ca60043591610a0d8160008581526020958187526001600160401b038383205416825260028752828220908252865281812060243582528652208251958680926114a4565b346102635760203660031901126102635760043561195181610bf4565b611959612690565b6001600160a01b039081169081156119ad57600754826bffffffffffffffffffffffff60a01b821617600755167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0600080a3005b604051631e4fbdf760e01b815260006004820152602490fd5b34610263576040366003190112610263576001600160401b03600435818111610263576119f79036906004016103c7565b9060243583811161026357611a109036906004016103c7565b9390928201906060838303126102635782358181116102635782611a35918501610e64565b9360208401359180831691828403610263576040860135918211610263576102ca97611a9588611abd96611a84611a9a95611a7b611ac49b611aa399611ac99e01610e64565b95810190612c6c565b9091906001600160a01b0316612ece565b612f4b565b91421115612ca2565b6001600160a01b0316600090815260086020526040902090565b5460ff1690565b612644565b60405191829182610990565b1561026357565b908092918237016000815290565b818110611af5575050565b60008155600101611aea565b9190601f8111611b1057505050565b6105ca926000526020600020906020601f840160051c83019310611b3c575b601f0160051c0190611aea565b9091508190611b2f565b9092916001600160401b0381116107b757611b6b81611b65845461146a565b84611b01565b6000601f8211600114611bac578190611b9d939495600092611ba1575b50508160011b916000199060031b1c19161790565b9055565b013590503880611b88565b601f19821694611bc184600052602060002090565b91805b878110611bfc575083600195969710611be2575b505050811b019055565b0135600019600384901b60f8161c19169055388080611bd8565b90926020600181928686013581550194019101611bc4565b81604051928392833781016000815203902090565b908060209392818452848401376000828201840152601f01601f1916010190565b9290611c639061056a9593604086526040860191611c29565b926020818503910152611c29565b60405190602082018281106001600160401b038211176107b75760405260008252565b3d15611cbf573d90611ca582610e12565b91611cb36040519384610bbc565b82523d6000602084013e565b606090565b8051601f1015611cd457603f0190565b611454565b908151811015611cd4570160200190565b90611d6a611d5d82611d4585611d36611d1d611d10836000526000602052604060002090565b546001600160401b031690565b6001600160401b03166000526004602052604060002090565b90600052602052604060002090565b9063ffffffff60e01b16600052602052604060002090565b546001600160a01b031690565b6001600160a01b039290838116611ecb5750611d88611d9491612080565b6001600160a01b031690565b91821615611ec4576040516301ffc9a760e01b6020820181815260248084018390528352929091601f199190611dcb604482610bbc565b6000809581925190885afa611dde611c94565b9015908115611eb7575b8115611e97575b50611e8f57604051602081019384526001600160e01b03199190911660248201526044918201815283928392909190611e289082610bbc565b5190855afa611e35611c94565b9015908115611e82575b8115611e54575b50611e4f575090565b905090565b6001600160f81b03199150611e7a90611e6c90611cc4565b516001600160f81b03191690565b161538611e46565b9050602081511090611e3f565b505050905090565b6001600160f81b03199150611eaf90611e6c90611cc4565b161538611def565b9050602081511090611de8565b5050600090565b9250505090565b91906000928084526020846020526040906001600160401b038287205416865260019260016020528287209087526020528186209060015b85811115611f205750505050505061056a611c71565b858116151580611f56575b611f3657841b611f0a565b808852919052948190209051925061056a915082906115869082906114a4565b50808852828252611f698489205461146a565b1515611f2b565b9092916001600160401b0381116107b757611f8f81611b65845461146a565b6000601f8211600114611fc0578190611b9d939495600092611ba15750508160011b916000199060031b1c19161790565b601f19821694611fd584600052602060002090565b91805b878110611ff5575083600195969710611be257505050811b019055565b90926020600181928686013581550194019101611fd8565b91602061056a938181520191611c29565b1561202557565b60405162461bcd60e51b815260206004820152601d60248201527f4e6f207065726d697373696f6e7320746f206d6f64696679206e616d650000006044820152606490fd5b634e487b7160e01b600052601160045260246000fd5b600090808252816020526001600160401b03604083205416825260026020526040822090825260205260408120603c82526020526115866120ca60408320604051928380926114a4565b8051156120db5761056a9150612810565b5090565b60001981019190821161096d57565b9190820391821161096d57565b9190612105612690565b60005b83518110156122335760019082156121a05761214461213a611aa361212d8489612239565b516001600160a01b031690565b805460ff19169055565b7f70f1a3dba165402559aaa92407aa69ed152f584fde0bc213bcf1c47acef771b661219661217561212d8489612239565b604080516001600160a01b0390921682526001602083015290918291820190565b0390a15b01612108565b6121cf828060a01b036121b38388612239565b51166001600160a01b0316600090815260086020526040902090565b805460ff1916831790557f70f1a3dba165402559aaa92407aa69ed152f584fde0bc213bcf1c47acef771b661222b61220a61212d8489612239565b604080516001600160a01b0390921682526000602083015290918291820190565b0390a161219a565b50509050565b8051821015611cd45760209160051b010190565b91909182516001600160401b0381116107b75761226e81611b65845461146a565b602080601f83116001146122ac57508190611b9d9394956000926122a15750508160011b916000199060031b1c19161790565b015190503880611b88565b90601f198316956122c285600052602060002090565b926000905b8882106122fe575050836001959697106122e557505050811b019055565b015160001960f88460031b161c19169055388080611bd8565b806001859682949686015181550195019301906122c7565b909161232360008361286f565b604051630178b8bf60e01b8152600481018290526001600160a01b03906020816024817f000000000000000000000000000000000000000000000000000000000000000086165afa9081156123f0576000916123c1575b501615158061239c575b61238f575050612a64565b61056a92509290926129d6565b506123bc60ff6123b683600052600c602052604060002090565b54161590565b612384565b6123e3915060203d6020116123e9575b6123db8183610bbc565b8101906126bc565b3861237a565b503d6123d1565b6126d1565b91906123ff612690565b6000928084526020600e60205260408520948351916801000000000000000083116107b75786548388558084106124aa575b506124486020869893980192600052602060002090565b96915b83831061248e57505050507f0df0b0cbb9f439eba06faac70607df7d7c1ec883582b7501d2e73b28e5262ffc9293506124896040519283928361262d565b0390a1565b6001828261249e8394518c61252b565b0198019201919661244b565b878352836020842091820191015b8181106124c55750612431565b806124d26001925461146a565b806124df575b50016124b8565b601f9081811184146124f75750508481555b386124d8565b836125199261250b85600052602060002090565b920160051c82019101611aea565b600081815260208120818355556124f1565b91909182516001600160401b0381116107b75761254c81611b65845461146a565b602080601f831160011461257f57508190611b9d9394956000926122a15750508160011b916000199060031b1c19161790565b90601f1983169561259585600052602060002090565b926000905b8882106125b8575050836001959697106122e557505050811b019055565b8060018596829496860151815501950193019061259a565b90808251908181526020809101926020808460051b8301019501936000915b8483106125ff5750505050505090565b909192939495848061261d600193601f198682030187528a51610512565b98019301930191949392906125ef565b60409061056a9392815281602082015201906125d0565b1561264b57565b60405162461bcd60e51b815260206004820152601c60248201527f5369676e61747572653a20496e76616c6964207369676e6174757265000000006044820152606490fd5b6007546001600160a01b031633036126a457565b60405163118cdaa760e01b8152336004820152602490fd5b90816020910312610263575161056a81610bf4565b6040513d6000823e3d90fd5b90816020910312610263575161056a816105b3565b6040516302571be360e01b8152600481018290526001600160a01b03919060209081816024817f000000000000000000000000000000000000000000000000000000000000000088165afa9081156123f0576000916127f3575b5083163314918215612760575b5050905090565b6040516341415eab60e01b8152600481019190915233602482015290929091508290829060449082907f0000000000000000000000000000000000000000000000000000000000000000165afa9182156123f0576000926127c6575b5050803880612759565b6127e59250803d106127ec575b6127dd8183610bbc565b8101906126dd565b38806127bc565b503d6127d3565b61280a9150823d84116123e9576123db8183610bbc565b3861274c565b6014815103610263576020015160601c90565b1561282a57565b60405162461bcd60e51b815260206004820152601d60248201527f6e616d65686173683a204a756e6b20617420656e64206f66206e616d650000006044820152606490fd5b90815181101561292e576128a061289a6001600160f81b03196128928486611cd9565b511660f81c90565b60ff1690565b908115612920576128cd6128c86128c0846128ba85612cfa565b87612f61565b935b83612d08565b612cfa565b90821561290557506128df919261286f565b6040805160208101928352808201939093528252906128ff606082610bbc565b51902090565b91505061291561291b92516120df565b14612823565b600090565b6128cd6128c86000936128c2565b60405162461bcd60e51b815260206004820152601e60248201527f726561644c6162656c3a20496e646578206f7574206f6620626f756e647300006044820152606490fd5b1561297a57565b60405162461bcd60e51b815260206004820152602e60248201527f436f756c64206e6f74207175657279207468652066616c6c6261636b2072657360448201526d1bdb1d995c8818dbdb9d1c9858dd60921b6064820152608490fd5b9060208101906000918280835183305afa936129f0611c94565b9480612a47575b612a40578352600a602052604083205492935083926001600160a01b0390811680612a38575060095416915b51915afa61056a612a32611c94565b91612973565b905091612a23565b5050505090565b50845160208601208452600b60205260ff604085205416156129f7565b90612a6e82612d15565b8015612b2f575b600052602091600e6020526040926040600020805491612a9483610bdd565b95612aa26040519788610bbc565b83875260208701926000526020600020906000935b858510612b0c578888888251612ded5760405162461bcd60e51b815260206004820152601860248201527f4e6f207265736f756c74696f6e2075726c7320666f756e6400000000000000006044820152606490fd5b60018481928451612b2181611586818a6114a4565b815201930194019391612ab7565b5061270f612a75565b9190811015611cd45760051b81013590601e19813603018212156102635701908135916001600160401b038311610263576020018236038113610263579190565b906024116102635760040190602090565b359060208110612b98575090565b6000199060200360031b1b1690565b15612bae57565b60405162461bcd60e51b815260206004820152603460248201527f6d756c746963616c6c3a20416c6c207265636f726473206d7573742068617665604482015273040c240dac2e8c6d0d2dcce40dcc2dacad0c2e6d60631b6064820152608490fd5b60405190604082018281106001600160401b038211176107b7576040526014825260203681840137565b90612c4482610e12565b612c516040519182610bbc565b8281528092612c62601f1991610e12565b0190602036910137565b91906040838203126102635782356001600160401b03811161026357602091612c96918501610e64565b92013561056a81610bf4565b15612ca957565b60405162461bcd60e51b8152602060048201526024808201527f5369676e617475726556657269666965723a205369676e6174757265206578706044820152631a5c995960e21b6064820152608490fd5b906001820180921161096d57565b9190820180921161096d57565b80612d226000809361286f565b805b612d2d57505090565b808352602091600c8352600192836040862001541515600014612d67575050612d62919250600052600c602052604060002090565b015490565b90809392505115611cd457612d819083015160f81c612cfa565b91612d95612d908483516120ee565b612c3a565b9284835b612db2575b50505050612dac828261286f565b80612d24565b8451811015612de8578381612dd4611e6c612dce849587612d08565b87611cd9565b881a612de08289611cd9565b530190612d99565b612d9e565b612e24612e9a9392612ead612eca93612e366040938451958693639061b92360e01b60208601528660248601526064850190610512565b83810360231901604485015290610512565b0391612e4a601f1993848101865285610bbc565b612e7581519382602086015284612e646060820188610512565b308583015203908101855284610bbc565b51630556f18360e41b815230600482015260a0602482015295869560a48701906125d0565b6003199384878303016044880152610512565b631e9a9a5f60e31b60648601528481039092016084850152610512565b0390fd5b92909160208151910120906020815191012090604051926020840194601960f81b86526bffffffffffffffffffffffff199060601b1660228501526001600160401b0360c01b9060c01b166036840152603e830152605e820152605e8152608081018181106001600160401b038211176107b75760405251902090565b61056a91612f5891612f7b565b90929192612fd7565b9082810180821161096d5782511061026357016020012090565b8151919060418303612fac57612fa592506020820151906060604084015193015160001a90613064565b9192909190565b505060009160029190565b60041115612fc157565b634e487b7160e01b600052602160045260246000fd5b612fe081612fb7565b80612fe9575050565b612ff281612fb7565b6001810361300c5760405163f645eedf60e01b8152600490fd5b61301581612fb7565b600281036130365760405163fce698f760e01b815260048101839052602490fd5b80613042600392612fb7565b1461304a5750565b6040516335e2f38360e21b81526004810191909152602490fd5b91907f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a084116130dc57926020929160ff608095604051948552168484015260408301526060820152600092839182805260015afa156123f05780516001600160a01b038116156130d357918190565b50809160019190565b5050506000916003919056fea26469706673582212202fe88d8f5451b07275d5fd575be90c61e6593b2c9ecd650366f83aeb2e12dab864736f6c63430008180033000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000c2e074ec69a0dfb2997ba6c7d2e1e000000000000000000000000d4416b13d2b3a9abae7acd5d6c2bbdbe25686401000000000000000000000000231b0ee14048e9dccd1d247744d114a4eb5e8e630000000000000000000000000000000000000000000000000000000000000001000000000000000000000000740bdb3d297f951ad44bef7216ddd2cda339940b
Deployed Bytecode
0x6080604052600436101561001257600080fd5b60003560e01c806301ffc9a71461024757806310f13a8c14610242578063124a319c1461023d5780632203ab56146102385780632931570214610233578063304e6ade1461022e578063341e9393146102295780633603d758146102245780633b3b57de1461021f57806359d1d43c1461021a578063623195b014610215578063691f343114610210578063715018a61461020b5780637357c5671461020657806377372213146102015780637d85f6e2146101fc5780638b95dd71146101f75780638da5cb5b146101f25780638ed91c46146101ed5780639061b923146101e8578063a4c28248146101e3578063ac9650d8146101de578063aea9467d146101d9578063b9288916146101d4578063bc1c58d1146101cf578063bd47daa3146101ca578063c315b474146101c5578063ce8f6078146101c0578063d5fa2b00146101bb578063d700ff33146101b6578063e32954eb146101b1578063e59d895d146101ac578063f1cb7e06146101a7578063f2fde38b146101a25763f4d4d2f81461019d57600080fd5b6119c6565b611934565b6118d7565b611813565b6116fe565b6116c9565b6115cb565b611591565b61153a565b61139d565b61134e565b61131a565b6112d3565b6111f1565b611046565b610fdb565b610fb2565b610f89565b610e7f565b610dc9565b610ca1565b610c05565b610b45565b610adb565b610a1c565b6109a1565b610972565b6108c5565b6107bc565b61064a565b6105cc565b610584565b6104da565b6103f4565b61027f565b600435906001600160e01b03198216820361026357565b600080fd5b602435906001600160e01b03198216820361026357565b34610263576020366003190112610263576102ca6001600160e01b03196102a461024c565b16639061b92360e01b81149081156102ce575b5060405190151581529081906020820190565b0390f35b631674750f60e21b8114915081156102e8575b50386102b7565b63691f343160e01b811491508115610302575b50386102e1565b6304928c6760e21b81149150811561031c575b50386102fb565b63bc1c58d160e01b811491508115610336575b5038610315565b631d9dabef60e11b8114915081156103b6575b8115610357575b503861032f565b631101d5ab60e11b811491508115610371575b5038610350565b63d700ff3360e01b81149150811561038b575b503861036a565b634fbf043360e01b8114915081156103a5575b5038610384565b6301ffc9a760e01b1490503861039e565b6378e5bf0360e11b81149150610349565b9181601f84011215610263578235916001600160401b038311610263576020838186019501011161026357565b34610263576060366003190112610263576001600160401b03600435602435828111610263576104289036906004016103c7565b604492919235848111610263576104439036906004016103c7565b91909361044f846126f2565b15610263576104d47f448bc014f1536726cf8d54ff3d6481ed3cbc683c2591ca204274009afa09b1a1936000978689528860205260408920541688526006602052604088208689526020526104bd818860408b20602060405180928a8a83378a820190815203019020611b46565b6104c78484611c14565b9660405194859485611c4a565b0390a380f35b346102635760403660031901126102635760206105006104f8610268565b600435611cea565b6040516001600160a01b039091168152f35b919082519283825260005b84811061053e575050826000602080949584010152601f8019910116010190565b60208183018101518483018201520161051d565b90604061056a92603c81528160208201520190610512565b90565b60409061056a939281528160208201520190610512565b34610263576040366003190112610263576105a3602435600435611ed2565b906102ca6040519283928361056d565b8015150361026357565b602435906105ca826105b3565b565b34610263576040366003190112610263576106156024356105ec816105b3565b6105f4612690565b600435600052600d60205260406000209060ff801983541691151516179055565b005b9060406003198301126102635760043591602435906001600160401b03821161026357610646916004016103c7565b9091565b346102635761065836610617565b9091610663816126f2565b1561026357600091818352602093836020526001600160401b03806040862054168552600360205260408520848652602052604085209083116107b7576106b4836106ae835461146a565b83611b01565b8495601f84116001146107295750610706838087987fe379c1624ed7e714cc0937528a32359d69d5281337765313dba4e081b72d757897989161071e575b508160011b916000199060031b1c19161790565b90555b6107186040519283928361200d565b0390a280f35b9050840135386106f2565b601f1984169661073e83600052602060002090565b9187905b89821061079f575050847fe379c1624ed7e714cc0937528a32359d69d5281337765313dba4e081b72d757896979810610785575b5050600183811b019055610709565b830135600019600386901b60f8161c191690553880610776565b80600184958294958901358155019401920190610742565b610ba6565b34610263576040366003190112610263576004356024356107e46107df836126f2565b61201e565b80600052600d60205260ff6040600020541615610874578161086f60016108367ffb370bde575cc90b84f91138780a4144849a157773e7bc467236da4842345e4295600052600c602052604060002090565b01549280600161085085600052600c602052604060002090565b0155604051938493846040919493926060820195825260208201520152565b0390a1005b60405162461bcd60e51b8152602060048201526024808201527f556e737570706f72746564207265736f6c7574696f6e20747970652070726f766044820152631a59195960e21b6064820152608490fd5b34610263576020366003190112610263576004356108e2816126f2565b156102635760009080825281602052604082208054906001600160401b038083169181831461096d577fc6621ccb8f3f5a04bb6502154b2caf6adf5983fe76dfef1cfc9c42e3579db44493826001610718950116906001600160401b03191617905583855284602052604085205416604051918291829190916001600160401b036020820193169052565b61206a565b34610263576020366003190112610263576020610500600435612080565b90602061056a928181520190610512565b3461026357610a06610a0d6102ca6109b836610617565b600094919492808452602095869185835260409586916001600160401b03838320541682526006855282822090825284522083865194859384378201908152030190208251958680926114a4565b0385610bbc565b51928284938452830190610512565b34610263576060366003190112610263576001600160401b0360243560043560443583811161026357610a539036906004016103c7565b610a5c836126f2565b1561026357600019840184811161096d57841661026357610ab491600095848752866020526040872054168652600160205260408620848752602052610aaf856040882090600052602052604060002090565b611f70565b7faa121bbeef5f32f5961a2a28966e769023910fc9479059ee3495d4c1a696efe38380a380f35b346102635760208060031936011261026357610b2a90610b3160406004356000908082528185526001600160401b038383205416825260058552828220908252845220604051938480926114a4565b0383610bbc565b6102ca604051928284938452830190610512565b3461026357600080600319360112610ba357610b5f612690565b600780546001600160a01b0319811690915581906001600160a01b03167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e08280a380f35b80fd5b634e487b7160e01b600052604160045260246000fd5b90601f801991011681019081106001600160401b038211176107b757604052565b6001600160401b0381116107b75760051b60200190565b6001600160a01b0381160361026357565b34610263576040366003190112610263576004356001600160401b038111610263573660238201121561026357806004013590610c4182610bdd565b90610c4f6040519283610bbc565b8282526020926024602084019160051b8301019136831161026357602401905b828210610c885761061584610c826105bd565b906120fb565b8480918335610c9681610bf4565b815201910190610c6f565b3461026357610caf36610617565b9091610cba816126f2565b1561026357600091818352602093836020526001600160401b03806040862054168552600560205260408520848652602052604085209083116107b757610d05836106ae835461146a565b8495601f8411600114610d565750610706838087987fb7d29e911041e8d9b843369e890bcb72c9388692ba48b65ac54e7214c4c348f797989161071e57508160011b916000199060031b1c19161790565b601f19841696610d6b83600052602060002090565b9187905b898210610db1575050847fb7d29e911041e8d9b843369e890bcb72c9388692ba48b65ac54e7214c4c348f796979810610785575050600183811b019055610709565b80600184958294958901358155019401920190610d6f565b3461026357604036600319011261026357610615602435610de9816105b3565b610df1612690565b600435600052600b60205260406000209060ff801983541691151516179055565b6001600160401b0381116107b757601f01601f191660200190565b929192610e3982610e12565b91610e476040519384610bbc565b829481845281830111610263578281602093846000960137010152565b9080601f830112156102635781602061056a93359101610e2d565b34610263576060366003190112610263576001600160401b0360243560043560443583811161026357610eb6903690600401610e64565b90610ec0816126f2565b1561026357610f439281610f3e927f65412581168e88a1e60c6459d7f44ae83ad0832e670826c05a4e2476b57af75260405180610efe88878361056d565b0390a2603c8214610f46575b6000958187528660205260408720541686526002602052604086209086526020526040852090600052602052604060002090565b61224d565b80f35b807f52d7d861f09ab3d26239d492e8968629f95e9e318cf0b73bfddc441522a15fd26020610f7387612810565b6040516001600160a01b039091168152a2610f0a565b34610263576000366003190112610263576007546040516001600160a01b039091168152602090f35b34610263576000366003190112610263576009546040516001600160a01b039091168152602090f35b34610263576040366003190112610263576001600160401b036004358181116102635761100c903690600401610e64565b90602435908111610263576102ca9161102c611032923690600401610e64565b90612316565b604051918291602083526020830190610512565b346102635760403660031901126102635760043560243561106681610bf4565b6110726107df836126f2565b6000828152600a60205260409020546001600160a01b0382811691161461110d57816110ec826110cd7f90e6a2cff4e717c36e6aa27f1da038ed159ffb4bb9a028ac97b4e706c156562795600052600a602052604060002090565b80546001600160a01b0319166001600160a01b03909216919091179055565b604080519182526001600160a01b039092166020820152908190810161086f565b60405162461bcd60e51b815260206004820152602260248201527f53616d652066616c6c6261636b207265736f6c76657220616c72656164792073604482015261195d60f21b6064820152608490fd5b9181601f84011215610263578235916001600160401b038311610263576020808501948460051b01011161026357565b6020808201906020835283518092526040830192602060408460051b8301019501936000915b8483106111c35750505050505090565b90919293949584806111e1600193603f198682030187528a51610512565b98019301930191949392906111b3565b3461026357602080600319360112610263576004356001600160401b0381116102635761122290369060040161115d565b9161122c83610bdd565b9260409161123d6040519586610bbc565b818552601f1961124c83610bdd565b0160005b8181106112c45750505060005b81811061127257604051806102ca878261118d565b806000806112836001948689612b38565b90611292885180938193611adc565b0390305af46112a86112a2611c94565b91611ad5565b6112b28288612239565b526112bd8187612239565b500161125d565b60608782018401528201611250565b34610263576020366003190112610263576004356112f081610bf4565b6112f8612690565b600980546001600160a01b0319166001600160a01b0392909216919091179055005b3461026357602036600319011261026357600435600052600a602052602060018060a01b0360406000205416604051908152f35b346102635760208060031936011261026357610b2a90610b3160406004356000908082528185526001600160401b038383205416825260038552828220908252845220604051938480926114a4565b34610263576040366003190112610263576001600160401b03602480358281116102635736602382011215610263578060040135916113db83610bdd565b926113e96040519485610bbc565b8084526020946024602086019260051b850101933685116102635760248101925b85841061141d57610615876004356123f5565b8335838111610263578201366043820112156102635788916114498392369060448a8201359101610e2d565b81520193019261140a565b634e487b7160e01b600052603260045260246000fd5b90600182811c9216801561149a575b602083101461148457565b634e487b7160e01b600052602260045260246000fd5b91607f1691611479565b8054600093926114b38261146a565b9182825260209360019160018116908160001461151b57506001146114da575b5050505050565b90939495506000929192528360002092846000945b838610611507575050505001019038808080806114d3565b8054858701830152940193859082016114ef565b60ff19168685015250505090151560051b0101915038808080806114d3565b34610263576040366003190112610263576024356000906004358252600e60205260408220805482101561158d5761158691602084611032936102ca96522001604051928380926114a4565b0382610bbc565b8280fd5b3461026357602036600319011261026357600435600052600c602052604080600020600160ff825416910154825191151582526020820152f35b346102635760408060031936011261026357600435906024356115ed81610bf4565b6115f6836126f2565b1561026357611603612c10565b9060601b6020820152611615836126f2565b1561026357610f3e82847f65412581168e88a1e60c6459d7f44ae83ad0832e670826c05a4e2476b57af752610f439551806116508782610552565b0390a2847f52d7d861f09ab3d26239d492e8968629f95e9e318cf0b73bfddc441522a15fd2602061168086612810565b84516001600160a01b039091168152a2600094808652856020526001600160401b038287205416865260026020528186209086526020528420603c600052602052604060002090565b3461026357602036600319011261026357600435600052600060205260206001600160401b0360406000205416604051908152f35b3461026357604080600319360112610263576004356024356001600160401b0381116102635761173290369060040161115d565b61173e81949294610bdd565b9361174c6040519586610bbc565b818552601f1961175b83610bdd565b0160005b8181106118025750508315159360005b83811061178457604051806102ca898261118d565b600190866117d6575b60008061179b838888612b38565b906117aa8a5180938193611adc565b0390305af46117ba6112a2611c94565b6117c4828a612239565b526117cf8189612239565b500161176f565b6117fd836117f76117f16117eb858a8a612b38565b90612b79565b90612b8a565b14612ba7565b61178d565b806060602080938a0101520161175f565b346102635760603660031901126102635760043561182f610268565b906044359061183d82610bf4565b611846816126f2565b15610263577f7c69f06bea0bdef565b709e93a147836b0063ba2dd89f02d0b7e8d931e6a6daa60206000948386528582526001600160401b036040872054168652600482526040862084875282526118b8856110cd8360408a209063ffffffff60e01b16600052602052604060002090565b6040516001600160a01b0390951685526001600160e01b03191693a380f35b346102635760408060031936011261026357610a06906102ca60043591610a0d8160008581526020958187526001600160401b038383205416825260028752828220908252865281812060243582528652208251958680926114a4565b346102635760203660031901126102635760043561195181610bf4565b611959612690565b6001600160a01b039081169081156119ad57600754826bffffffffffffffffffffffff60a01b821617600755167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0600080a3005b604051631e4fbdf760e01b815260006004820152602490fd5b34610263576040366003190112610263576001600160401b03600435818111610263576119f79036906004016103c7565b9060243583811161026357611a109036906004016103c7565b9390928201906060838303126102635782358181116102635782611a35918501610e64565b9360208401359180831691828403610263576040860135918211610263576102ca97611a9588611abd96611a84611a9a95611a7b611ac49b611aa399611ac99e01610e64565b95810190612c6c565b9091906001600160a01b0316612ece565b612f4b565b91421115612ca2565b6001600160a01b0316600090815260086020526040902090565b5460ff1690565b612644565b60405191829182610990565b1561026357565b908092918237016000815290565b818110611af5575050565b60008155600101611aea565b9190601f8111611b1057505050565b6105ca926000526020600020906020601f840160051c83019310611b3c575b601f0160051c0190611aea565b9091508190611b2f565b9092916001600160401b0381116107b757611b6b81611b65845461146a565b84611b01565b6000601f8211600114611bac578190611b9d939495600092611ba1575b50508160011b916000199060031b1c19161790565b9055565b013590503880611b88565b601f19821694611bc184600052602060002090565b91805b878110611bfc575083600195969710611be2575b505050811b019055565b0135600019600384901b60f8161c19169055388080611bd8565b90926020600181928686013581550194019101611bc4565b81604051928392833781016000815203902090565b908060209392818452848401376000828201840152601f01601f1916010190565b9290611c639061056a9593604086526040860191611c29565b926020818503910152611c29565b60405190602082018281106001600160401b038211176107b75760405260008252565b3d15611cbf573d90611ca582610e12565b91611cb36040519384610bbc565b82523d6000602084013e565b606090565b8051601f1015611cd457603f0190565b611454565b908151811015611cd4570160200190565b90611d6a611d5d82611d4585611d36611d1d611d10836000526000602052604060002090565b546001600160401b031690565b6001600160401b03166000526004602052604060002090565b90600052602052604060002090565b9063ffffffff60e01b16600052602052604060002090565b546001600160a01b031690565b6001600160a01b039290838116611ecb5750611d88611d9491612080565b6001600160a01b031690565b91821615611ec4576040516301ffc9a760e01b6020820181815260248084018390528352929091601f199190611dcb604482610bbc565b6000809581925190885afa611dde611c94565b9015908115611eb7575b8115611e97575b50611e8f57604051602081019384526001600160e01b03199190911660248201526044918201815283928392909190611e289082610bbc565b5190855afa611e35611c94565b9015908115611e82575b8115611e54575b50611e4f575090565b905090565b6001600160f81b03199150611e7a90611e6c90611cc4565b516001600160f81b03191690565b161538611e46565b9050602081511090611e3f565b505050905090565b6001600160f81b03199150611eaf90611e6c90611cc4565b161538611def565b9050602081511090611de8565b5050600090565b9250505090565b91906000928084526020846020526040906001600160401b038287205416865260019260016020528287209087526020528186209060015b85811115611f205750505050505061056a611c71565b858116151580611f56575b611f3657841b611f0a565b808852919052948190209051925061056a915082906115869082906114a4565b50808852828252611f698489205461146a565b1515611f2b565b9092916001600160401b0381116107b757611f8f81611b65845461146a565b6000601f8211600114611fc0578190611b9d939495600092611ba15750508160011b916000199060031b1c19161790565b601f19821694611fd584600052602060002090565b91805b878110611ff5575083600195969710611be257505050811b019055565b90926020600181928686013581550194019101611fd8565b91602061056a938181520191611c29565b1561202557565b60405162461bcd60e51b815260206004820152601d60248201527f4e6f207065726d697373696f6e7320746f206d6f64696679206e616d650000006044820152606490fd5b634e487b7160e01b600052601160045260246000fd5b600090808252816020526001600160401b03604083205416825260026020526040822090825260205260408120603c82526020526115866120ca60408320604051928380926114a4565b8051156120db5761056a9150612810565b5090565b60001981019190821161096d57565b9190820391821161096d57565b9190612105612690565b60005b83518110156122335760019082156121a05761214461213a611aa361212d8489612239565b516001600160a01b031690565b805460ff19169055565b7f70f1a3dba165402559aaa92407aa69ed152f584fde0bc213bcf1c47acef771b661219661217561212d8489612239565b604080516001600160a01b0390921682526001602083015290918291820190565b0390a15b01612108565b6121cf828060a01b036121b38388612239565b51166001600160a01b0316600090815260086020526040902090565b805460ff1916831790557f70f1a3dba165402559aaa92407aa69ed152f584fde0bc213bcf1c47acef771b661222b61220a61212d8489612239565b604080516001600160a01b0390921682526000602083015290918291820190565b0390a161219a565b50509050565b8051821015611cd45760209160051b010190565b91909182516001600160401b0381116107b75761226e81611b65845461146a565b602080601f83116001146122ac57508190611b9d9394956000926122a15750508160011b916000199060031b1c19161790565b015190503880611b88565b90601f198316956122c285600052602060002090565b926000905b8882106122fe575050836001959697106122e557505050811b019055565b015160001960f88460031b161c19169055388080611bd8565b806001859682949686015181550195019301906122c7565b909161232360008361286f565b604051630178b8bf60e01b8152600481018290526001600160a01b03906020816024817f00000000000000000000000000000000000c2e074ec69a0dfb2997ba6c7d2e1e86165afa9081156123f0576000916123c1575b501615158061239c575b61238f575050612a64565b61056a92509290926129d6565b506123bc60ff6123b683600052600c602052604060002090565b54161590565b612384565b6123e3915060203d6020116123e9575b6123db8183610bbc565b8101906126bc565b3861237a565b503d6123d1565b6126d1565b91906123ff612690565b6000928084526020600e60205260408520948351916801000000000000000083116107b75786548388558084106124aa575b506124486020869893980192600052602060002090565b96915b83831061248e57505050507f0df0b0cbb9f439eba06faac70607df7d7c1ec883582b7501d2e73b28e5262ffc9293506124896040519283928361262d565b0390a1565b6001828261249e8394518c61252b565b0198019201919661244b565b878352836020842091820191015b8181106124c55750612431565b806124d26001925461146a565b806124df575b50016124b8565b601f9081811184146124f75750508481555b386124d8565b836125199261250b85600052602060002090565b920160051c82019101611aea565b600081815260208120818355556124f1565b91909182516001600160401b0381116107b75761254c81611b65845461146a565b602080601f831160011461257f57508190611b9d9394956000926122a15750508160011b916000199060031b1c19161790565b90601f1983169561259585600052602060002090565b926000905b8882106125b8575050836001959697106122e557505050811b019055565b8060018596829496860151815501950193019061259a565b90808251908181526020809101926020808460051b8301019501936000915b8483106125ff5750505050505090565b909192939495848061261d600193601f198682030187528a51610512565b98019301930191949392906125ef565b60409061056a9392815281602082015201906125d0565b1561264b57565b60405162461bcd60e51b815260206004820152601c60248201527f5369676e61747572653a20496e76616c6964207369676e6174757265000000006044820152606490fd5b6007546001600160a01b031633036126a457565b60405163118cdaa760e01b8152336004820152602490fd5b90816020910312610263575161056a81610bf4565b6040513d6000823e3d90fd5b90816020910312610263575161056a816105b3565b6040516302571be360e01b8152600481018290526001600160a01b03919060209081816024817f00000000000000000000000000000000000c2e074ec69a0dfb2997ba6c7d2e1e88165afa9081156123f0576000916127f3575b5083163314918215612760575b5050905090565b6040516341415eab60e01b8152600481019190915233602482015290929091508290829060449082907f000000000000000000000000d4416b13d2b3a9abae7acd5d6c2bbdbe25686401165afa9182156123f0576000926127c6575b5050803880612759565b6127e59250803d106127ec575b6127dd8183610bbc565b8101906126dd565b38806127bc565b503d6127d3565b61280a9150823d84116123e9576123db8183610bbc565b3861274c565b6014815103610263576020015160601c90565b1561282a57565b60405162461bcd60e51b815260206004820152601d60248201527f6e616d65686173683a204a756e6b20617420656e64206f66206e616d650000006044820152606490fd5b90815181101561292e576128a061289a6001600160f81b03196128928486611cd9565b511660f81c90565b60ff1690565b908115612920576128cd6128c86128c0846128ba85612cfa565b87612f61565b935b83612d08565b612cfa565b90821561290557506128df919261286f565b6040805160208101928352808201939093528252906128ff606082610bbc565b51902090565b91505061291561291b92516120df565b14612823565b600090565b6128cd6128c86000936128c2565b60405162461bcd60e51b815260206004820152601e60248201527f726561644c6162656c3a20496e646578206f7574206f6620626f756e647300006044820152606490fd5b1561297a57565b60405162461bcd60e51b815260206004820152602e60248201527f436f756c64206e6f74207175657279207468652066616c6c6261636b2072657360448201526d1bdb1d995c8818dbdb9d1c9858dd60921b6064820152608490fd5b9060208101906000918280835183305afa936129f0611c94565b9480612a47575b612a40578352600a602052604083205492935083926001600160a01b0390811680612a38575060095416915b51915afa61056a612a32611c94565b91612973565b905091612a23565b5050505090565b50845160208601208452600b60205260ff604085205416156129f7565b90612a6e82612d15565b8015612b2f575b600052602091600e6020526040926040600020805491612a9483610bdd565b95612aa26040519788610bbc565b83875260208701926000526020600020906000935b858510612b0c578888888251612ded5760405162461bcd60e51b815260206004820152601860248201527f4e6f207265736f756c74696f6e2075726c7320666f756e6400000000000000006044820152606490fd5b60018481928451612b2181611586818a6114a4565b815201930194019391612ab7565b5061270f612a75565b9190811015611cd45760051b81013590601e19813603018212156102635701908135916001600160401b038311610263576020018236038113610263579190565b906024116102635760040190602090565b359060208110612b98575090565b6000199060200360031b1b1690565b15612bae57565b60405162461bcd60e51b815260206004820152603460248201527f6d756c746963616c6c3a20416c6c207265636f726473206d7573742068617665604482015273040c240dac2e8c6d0d2dcce40dcc2dacad0c2e6d60631b6064820152608490fd5b60405190604082018281106001600160401b038211176107b7576040526014825260203681840137565b90612c4482610e12565b612c516040519182610bbc565b8281528092612c62601f1991610e12565b0190602036910137565b91906040838203126102635782356001600160401b03811161026357602091612c96918501610e64565b92013561056a81610bf4565b15612ca957565b60405162461bcd60e51b8152602060048201526024808201527f5369676e617475726556657269666965723a205369676e6174757265206578706044820152631a5c995960e21b6064820152608490fd5b906001820180921161096d57565b9190820180921161096d57565b80612d226000809361286f565b805b612d2d57505090565b808352602091600c8352600192836040862001541515600014612d67575050612d62919250600052600c602052604060002090565b015490565b90809392505115611cd457612d819083015160f81c612cfa565b91612d95612d908483516120ee565b612c3a565b9284835b612db2575b50505050612dac828261286f565b80612d24565b8451811015612de8578381612dd4611e6c612dce849587612d08565b87611cd9565b881a612de08289611cd9565b530190612d99565b612d9e565b612e24612e9a9392612ead612eca93612e366040938451958693639061b92360e01b60208601528660248601526064850190610512565b83810360231901604485015290610512565b0391612e4a601f1993848101865285610bbc565b612e7581519382602086015284612e646060820188610512565b308583015203908101855284610bbc565b51630556f18360e41b815230600482015260a0602482015295869560a48701906125d0565b6003199384878303016044880152610512565b631e9a9a5f60e31b60648601528481039092016084850152610512565b0390fd5b92909160208151910120906020815191012090604051926020840194601960f81b86526bffffffffffffffffffffffff199060601b1660228501526001600160401b0360c01b9060c01b166036840152603e830152605e820152605e8152608081018181106001600160401b038211176107b75760405251902090565b61056a91612f5891612f7b565b90929192612fd7565b9082810180821161096d5782511061026357016020012090565b8151919060418303612fac57612fa592506020820151906060604084015193015160001a90613064565b9192909190565b505060009160029190565b60041115612fc157565b634e487b7160e01b600052602160045260246000fd5b612fe081612fb7565b80612fe9575050565b612ff281612fb7565b6001810361300c5760405163f645eedf60e01b8152600490fd5b61301581612fb7565b600281036130365760405163fce698f760e01b815260048101839052602490fd5b80613042600392612fb7565b1461304a5750565b6040516335e2f38360e21b81526004810191909152602490fd5b91907f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a084116130dc57926020929160ff608095604051948552168484015260408301526060820152600092839182805260015afa156123f05780516001600160a01b038116156130d357918190565b50809160019190565b5050506000916003919056fea26469706673582212202fe88d8f5451b07275d5fd575be90c61e6593b2c9ecd650366f83aeb2e12dab864736f6c63430008180033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000c2e074ec69a0dfb2997ba6c7d2e1e000000000000000000000000d4416b13d2b3a9abae7acd5d6c2bbdbe25686401000000000000000000000000231b0ee14048e9dccd1d247744d114a4eb5e8e630000000000000000000000000000000000000000000000000000000000000001000000000000000000000000740bdb3d297f951ad44bef7216ddd2cda339940b
-----Decoded View---------------
Arg [0] : _signers (address[]): 0x740Bdb3D297F951AD44BEf7216Ddd2cdA339940b
Arg [1] : ens (address): 0x00000000000C2E074eC69A0dFb2997BA6C7d2e1e
Arg [2] : nameWrapper (address): 0xD4416b13d2b3a9aBae7AcD5D6C2BbDBE25686401
Arg [3] : _fallbackResolver (address): 0x231b0Ee14048e9dCcD1d247744d114a4EB5E8E63
-----Encoded View---------------
6 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000080
Arg [1] : 00000000000000000000000000000000000c2e074ec69a0dfb2997ba6c7d2e1e
Arg [2] : 000000000000000000000000d4416b13d2b3a9abae7acd5d6c2bbdbe25686401
Arg [3] : 000000000000000000000000231b0ee14048e9dccd1d247744d114a4eb5e8e63
Arg [4] : 0000000000000000000000000000000000000000000000000000000000000001
Arg [5] : 000000000000000000000000740bdb3d297f951ad44bef7216ddd2cda339940b
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 34 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|
Loading...
Loading
Loading...
Loading
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.