Source Code
Overview
ETH Balance
0 ETH
More Info
ContractCreator
Multichain Info
N/A
Latest 1 from a total of 1 transactions
| Transaction Hash |
Method
|
Block
|
From
|
To
|
Amount
|
||||
|---|---|---|---|---|---|---|---|---|---|
| Set Value | 5822814 | 674 days ago | IN | 0 ETH | 0.00607887 |
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Loading...
Loading
Loading...
Loading
Loading...
Loading
This contract may be a proxy contract. Click on More Options and select Is this a proxy? to confirm and enable the "Read as Proxy" & "Write as Proxy" tabs.
Contract Name:
IPResolver
Compiler Version
v0.8.23+commit.f704f362
Optimization Enabled:
Yes with 20000 runs
Other Settings:
paris EvmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { ResolverBase } from "./ResolverBase.sol";
import { KeyValueResolver } from "../resolvers/KeyValueResolver.sol";
import { IP_RESOLVER_MODULE_KEY } from "../lib/modules/Module.sol";
/// @title IP Resolver
/// @notice Canonical IP resolver contract used for Story Protocol.
/// TODO: Add support for interface resolvers, where one can add a contract
/// and supported interface (address, interfaceId) to tie to an IP asset.
/// TODO: Add support for multicall, so multiple records may be set at once.
contract IPResolver is KeyValueResolver {
string public constant override name = IP_RESOLVER_MODULE_KEY;
constructor(address accessController, address ipAssetRegistry) ResolverBase(accessController, ipAssetRegistry) {}
/// @notice IERC165 interface support.
function supportsInterface(bytes4 id) public view virtual override returns (bool) {
return super.supportsInterface(id);
}
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { BaseModule } from "../modules/BaseModule.sol";
import { IResolver } from "../interfaces/resolvers/IResolver.sol";
import { AccessControlled } from "../access/AccessControlled.sol";
/// @notice IP Resolver Base Contract
abstract contract ResolverBase is IResolver, BaseModule, AccessControlled {
constructor(address accessController, address assetRegistry) AccessControlled(accessController, assetRegistry) {}
/// @notice IERC165 interface support.
function supportsInterface(bytes4 id) public view virtual override(BaseModule, IResolver) returns (bool) {
return id == type(IResolver).interfaceId || super.supportsInterface(id);
}
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { IKeyValueResolver } from "../interfaces/resolvers/IKeyValueResolver.sol";
import { ResolverBase } from "../resolvers/ResolverBase.sol";
/// @title Key Value Resolver
/// @notice Resolver used for returning values associated with keys. This is the
/// preferred approach for adding additional attribution to IP that the
/// IP originator thinks is beneficial to have on chain.
abstract contract KeyValueResolver is IKeyValueResolver, ResolverBase {
/// @dev Stores key-value pairs associated with each IP.
mapping(address => mapping(string => string)) internal _values;
/// @notice Sets the string value for a specified key of an IP ID.
/// @dev Enforced to be only callable by users with valid permission to call on behalf of the ipId.
/// @param ipId The canonical identifier of the IP asset.
/// @param key The string parameter key to update.
/// @param val The value to set for the specified key.
function setValue(address ipId, string calldata key, string calldata val) external virtual verifyPermission(ipId) {
_values[ipId][key] = val;
emit KeyValueSet(ipId, key, val);
}
/// @notice Retrieves the string value associated with a key for an IP asset.
/// @param key The string parameter key to query.
/// @return value The value associated with the specified key.
function value(address ipId, string calldata key) external view virtual returns (string memory) {
return _values[ipId][key];
}
/// @notice IERC165 interface support.
function supportsInterface(bytes4 id) public view virtual override returns (bool) {
return id == type(IKeyValueResolver).interfaceId || super.supportsInterface(id);
}
}// SPDX-License-Identifier: BUSL-1.1 pragma solidity 0.8.23; // Default Module Type, all modules in this type by default string constant MODULE_TYPE_DEFAULT = "MODULE"; string constant MODULE_TYPE_HOOK = "HOOK_MODULE"; // String values for core protocol modules. string constant IP_RESOLVER_MODULE_KEY = "IP_RESOLVER_MODULE"; // String values for core protocol modules. string constant REGISTRATION_MODULE_KEY = "REGISTRATION_MODULE"; // String values for core protocol modules. string constant LICENSING_MODULE_KEY = "LICENSING_MODULE"; // String values for core protocol modules. string constant DISPUTE_MODULE_KEY = "DISPUTE_MODULE"; string constant ROYALTY_MODULE_KEY = "ROYALTY_MODULE"; string constant TOKEN_WITHDRAWAL_MODULE_KEY = "TOKEN_MANAGEMENT_MODULE";
// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { IERC165, ERC165 } from "@openzeppelin/contracts/utils/introspection/ERC165.sol";
import { IModule } from "../interfaces/modules/base/IModule.sol";
/// @title BaseModule
/// @notice Base implementation for all modules in Story Protocol.
abstract contract BaseModule is ERC165, IModule {
/// @notice IERC165 interface support.
function supportsInterface(bytes4 interfaceId) public view virtual override(ERC165, IERC165) returns (bool) {
return interfaceId == type(IModule).interfaceId || super.supportsInterface(interfaceId);
}
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
/// @notice Resolver Interface
interface IResolver {
/// @notice Checks whether the resolver IP interface is supported.
function supportsInterface(bytes4 id) external view returns (bool);
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { IAccessController } from "../interfaces/IAccessController.sol";
import { IPAccountChecker } from "../lib/registries/IPAccountChecker.sol";
import { IIPAccountRegistry } from "../interfaces/registries/IIPAccountRegistry.sol";
import { Errors } from "../lib/Errors.sol";
/// @title AccessControlled
/// @notice Provides a base contract for access control functionalities.
/// @dev This abstract contract implements basic access control mechanisms with an emphasis
/// on IP account verification and permission checks.
/// It is designed to be used as a base contract for other contracts that require access control.
/// It provides modifiers and functions to verify if the caller has the necessary permission
/// and is a registered IP account.
abstract contract AccessControlled {
using IPAccountChecker for IIPAccountRegistry;
/// @notice The IAccessController instance for permission checks.
IAccessController public immutable ACCESS_CONTROLLER;
/// @notice The IIPAccountRegistry instance for IP account verification.
IIPAccountRegistry public immutable IP_ACCOUNT_REGISTRY;
/// @dev Initializes the contract by setting the ACCESS_CONTROLLER and IP_ACCOUNT_REGISTRY addresses.
/// @param accessController The address of the AccessController contract.
/// @param ipAccountRegistry The address of the IPAccountRegistry contract.
constructor(address accessController, address ipAccountRegistry) {
if (accessController == address(0)) revert Errors.AccessControlled__ZeroAddress();
if (ipAccountRegistry == address(0)) revert Errors.AccessControlled__ZeroAddress();
ACCESS_CONTROLLER = IAccessController(accessController);
IP_ACCOUNT_REGISTRY = IIPAccountRegistry(ipAccountRegistry);
}
/// @notice Verifies that the caller has the necessary permission for the given IPAccount.
/// @dev Modifier that calls _verifyPermission to check if the provided IP account has the required permission.
/// modules can use this modifier to check if the caller has the necessary permission.
/// @param ipAccount The address of the IP account to verify.
modifier verifyPermission(address ipAccount) {
_verifyPermission(ipAccount);
_;
}
/// @notice Ensures that the caller is a registered IP account.
/// @dev Modifier that checks if the msg.sender is a registered IP account.
/// modules can use this modifier to check if the caller is a registered IP account.
/// so that enforce only registered IP Account can call the functions.
modifier onlyIpAccount() {
if (!IP_ACCOUNT_REGISTRY.isIpAccount(msg.sender)) {
revert Errors.AccessControlled__CallerIsNotIpAccount(msg.sender);
}
_;
}
/// @dev Internal function to verify if the caller (msg.sender) has the required permission to execute
/// the function on provided ipAccount.
/// @param ipAccount The address of the IP account to verify.
function _verifyPermission(address ipAccount) internal view {
if (!IP_ACCOUNT_REGISTRY.isIpAccount(ipAccount)) {
revert Errors.AccessControlled__NotIpAccount(ipAccount);
}
if (msg.sender != ipAccount) {
// revert if the msg.sender does not have permission
ACCESS_CONTROLLER.checkPermission(ipAccount, msg.sender, address(this), msg.sig);
}
}
/// @dev Internal function to check if the caller (msg.sender) has the required permission to execute
/// the function on provided ipAccount, returning a boolean.
/// @param ipAccount The address of the IP account to check.
/// @return bool Returns true if the caller has permission, false otherwise.
function _hasPermission(address ipAccount) internal view returns (bool) {
if (!IP_ACCOUNT_REGISTRY.isIpAccount(ipAccount)) {
return false;
}
if (msg.sender == ipAccount) {
return true;
}
try ACCESS_CONTROLLER.checkPermission(ipAccount, msg.sender, address(this), msg.sig) {
return true;
} catch {
return false;
}
}
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
/// @title Key Value Resolver Interface
interface IKeyValueResolver {
/// @notice Emits when a new key-value pair is set for the resolver.
event KeyValueSet(address indexed ipId, string indexed key, string value);
/// @notice Sets the string value for a specified key of an IP ID.
/// @dev Enforced to be only callable by users with valid permission to call on behalf of the ipId.
/// @param ipId The canonical identifier of the IP asset.
/// @param key The string parameter key to update.
/// @param val The value to set for the specified key.
function setValue(address ipId, string calldata key, string calldata val) external;
/// @notice Retrieves the string value associated with a key for an IP asset.
/// @param key The string parameter key to query.
/// @return value The value associated with the specified key.
function value(address ipId, string calldata key) external view returns (string memory);
}// 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: BUSL-1.1
pragma solidity 0.8.23;
import { IERC165 } from "@openzeppelin/contracts/utils/introspection/IERC165.sol";
/// @notice Module Interface
interface IModule is IERC165 {
/// @notice Returns the string identifier associated with the module.
function name() external returns (string memory);
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { AccessPermission } from "../lib/AccessPermission.sol";
interface IAccessController {
/// @notice Emitted when a permission is set.
/// @param ipAccount The address of the IP account that grants the permission for `signer`
/// @param signer The address that can call `to` on behalf of the IP account
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
/// @param permission The permission level
event PermissionSet(
address ipAccountOwner,
address indexed ipAccount,
address indexed signer,
address indexed to,
bytes4 func,
uint8 permission
);
/// @notice Sets a batch of permissions in a single transaction.
/// @dev This function allows setting multiple permissions at once. Pausable.
/// @param permissions An array of `Permission` structs, each representing the permission to be set.
function setBatchPermissions(AccessPermission.Permission[] memory permissions) external;
/// @notice Sets the permission for all IPAccounts
/// @dev Enforced to be only callable by the protocol admin in governance.
/// @param signer The address that can call `to` on behalf of the IP account
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
/// @param permission The new permission level
function setGlobalPermission(address signer, address to, bytes4 func, uint8 permission) external;
/// @notice Sets the permission for a specific function call
/// @dev Each policy is represented as a mapping from an IP account address to a signer address to a recipient
/// address to a function selector to a permission level. The permission level can be 0 (ABSTAIN), 1 (ALLOW), or
/// 2 (DENY).
/// @dev By default, all policies are set to 0 (ABSTAIN), which means that the permission is not set.
/// The owner of ipAccount by default has all permission.
/// address(0) => wildcard
/// bytes4(0) => wildcard
/// Specific permission overrides wildcard permission.
/// @param ipAccount The address of the IP account that grants the permission for `signer`
/// @param signer The address that can call `to` on behalf of the `ipAccount`
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
/// @param permission The new permission level
function setPermission(address ipAccount, address signer, address to, bytes4 func, uint8 permission) external;
/// @notice Checks the permission level for a specific function call. Reverts if permission is not granted.
/// Otherwise, the function is a noop.
/// @dev This function checks the permission level for a specific function call.
/// If a specific permission is set, it overrides the general (wildcard) permission.
/// If the current level permission is ABSTAIN, the final permission is determined by the upper level.
/// @param ipAccount The address of the IP account that grants the permission for `signer`
/// @param signer The address that can call `to` on behalf of the `ipAccount`
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
function checkPermission(address ipAccount, address signer, address to, bytes4 func) external view;
/// @notice Returns the permission level for a specific function call.
/// @param ipAccount The address of the IP account that grants the permission for `signer`
/// @param signer The address that can call `to` on behalf of the `ipAccount`
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
/// @return permission The current permission level for the function call on `to` by the `signer` for `ipAccount`
function getPermission(address ipAccount, address signer, address to, bytes4 func) external view returns (uint8);
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { ERC165Checker } from "@openzeppelin/contracts/utils/introspection/ERC165Checker.sol";
import { IERC6551Account } from "erc6551/interfaces/IERC6551Account.sol";
import { IIPAccountRegistry } from "../../interfaces/registries/IIPAccountRegistry.sol";
import { IIPAccount } from "../..//interfaces/IIPAccount.sol";
/// @title IPAccountChecker
/// @dev This library provides utility functions to check the registration and validity of IP Accounts.
/// It uses the ERC165 standard for contract introspection and the IIPAccountRegistry interface
/// for account registration checks.
library IPAccountChecker {
/// @notice Returns true if the IPAccount is registered.
/// @param chainId_ The chain ID where the IP Account is located.
/// @param tokenContract_ The address of the token contract associated with the IP Account.
/// @param tokenId_ The ID of the token associated with the IP Account.
/// @return True if the IP Account is registered, false otherwise.
function isRegistered(
IIPAccountRegistry ipAccountRegistry_,
uint256 chainId_,
address tokenContract_,
uint256 tokenId_
) external view returns (bool) {
return ipAccountRegistry_.ipAccount(chainId_, tokenContract_, tokenId_).code.length != 0;
}
/// @notice Checks if the given address is a valid IP Account.
/// @param ipAccountRegistry_ The IP Account registry contract.
/// @param ipAccountAddress_ The address to check.
/// @return True if the address is a valid IP Account, false otherwise.
function isIpAccount(
IIPAccountRegistry ipAccountRegistry_,
address ipAccountAddress_
) external view returns (bool) {
if (ipAccountAddress_ == address(0)) return false;
if (ipAccountAddress_.code.length == 0) return false;
if (!ERC165Checker.supportsERC165(ipAccountAddress_)) return false;
if (!ERC165Checker.supportsInterface(ipAccountAddress_, type(IERC6551Account).interfaceId)) return false;
if (!ERC165Checker.supportsInterface(ipAccountAddress_, type(IIPAccount).interfaceId)) return false;
(uint chainId, address tokenContract, uint tokenId) = IIPAccount(payable(ipAccountAddress_)).token();
return ipAccountAddress_ == ipAccountRegistry_.ipAccount(chainId, tokenContract, tokenId);
}
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
/// @title Interface for IP Account Registry
/// @notice This interface manages the registration and tracking of IP Accounts
interface IIPAccountRegistry {
/// @notice Event emitted when a new IP Account is created
/// @param account The address of the new IP Account
/// @param implementation The address of the IP Account implementation
/// @param chainId The chain ID where the token contract was deployed
/// @param tokenContract The address of the token contract associated with the IP Account
/// @param tokenId The ID of the token associated with the IP Account
event IPAccountRegistered(
address indexed account,
address indexed implementation,
uint256 indexed chainId,
address tokenContract,
uint256 tokenId
);
/// @notice Returns the IPAccount implementation address
function IP_ACCOUNT_IMPL() external view returns (address);
/// @notice Returns the IPAccount salt
function IP_ACCOUNT_SALT() external view returns (bytes32);
/// @notice Returns the public ERC6551 registry address
function ERC6551_PUBLIC_REGISTRY() external view returns (address);
/// @notice Deploys an IPAccount contract with the IPAccount implementation and returns the address of the new IP
/// @dev The IPAccount deployment deltegates to public ERC6551 Registry
/// @param chainId The chain ID where the IP Account will be created
/// @param tokenContract The address of the token contract to be associated with the IP Account
/// @param tokenId The ID of the token to be associated with the IP Account
/// @return ipAccountAddress The address of the newly created IP Account
function registerIpAccount(uint256 chainId, address tokenContract, uint256 tokenId) external returns (address);
/// @notice Returns the IPAccount address for the given NFT token.
/// @param chainId The chain ID where the IP Account is located
/// @param tokenContract The address of the token contract associated with the IP Account
/// @param tokenId The ID of the token associated with the IP Account
/// @return ipAccountAddress The address of the IP Account associated with the given NFT token
function ipAccount(uint256 chainId, address tokenContract, uint256 tokenId) external view returns (address);
/// @notice Returns the IPAccount implementation address.
/// @return The address of the IPAccount implementation
function getIPAccountImpl() external view returns (address);
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
/// @title Errors Library
/// @notice Library for all Story Protocol contract errors.
library Errors {
////////////////////////////////////////////////////////////////////////////
// Governance //
////////////////////////////////////////////////////////////////////////////
error Governance__OnlyProtocolAdmin();
error Governance__ZeroAddress();
error Governance__ProtocolPaused();
error Governance__InconsistentState();
error Governance__NewStateIsTheSameWithOldState();
error Governance__UnsupportedInterface(string interfaceName);
////////////////////////////////////////////////////////////////////////////
// IPAccount //
////////////////////////////////////////////////////////////////////////////
error IPAccount__InvalidSigner();
error IPAccount__InvalidSignature();
error IPAccount__ExpiredSignature();
error IPAccount__InvalidCalldata();
error IPAccount__InvalidAccessController();
////////////////////////////////////////////////////////////////////////////
// Module //
////////////////////////////////////////////////////////////////////////////
/// @notice The caller is not allowed to call the provided module.
error Module_Unauthorized();
////////////////////////////////////////////////////////////////////////////
// IPAccountRegistry //
////////////////////////////////////////////////////////////////////////////
error IPAccountRegistry_InvalidIpAccountImpl();
////////////////////////////////////////////////////////////////////////////
// IPAssetRegistry //
////////////////////////////////////////////////////////////////////////////
/// @notice The IP asset has already been registered.
error IPAssetRegistry__AlreadyRegistered();
/// @notice The IP account has already been created.
error IPAssetRegistry__IPAccountAlreadyCreated();
/// @notice The IP asset has not yet been registered.
error IPAssetRegistry__NotYetRegistered();
/// @notice The IP asset registrant is not authorized.
error IPAssetRegistry__RegistrantUnauthorized();
/// @notice The specified IP resolver is not valid.
error IPAssetRegistry__ResolverInvalid();
/// @notice Caller not authorized to perform the IP registry function call.
error IPAssetRegistry__Unauthorized();
/// @notice The deployed address of account doesn't match with IP ID.
error IPAssetRegistry__InvalidAccount();
/// @notice The metadata provider is not valid.
error IPAssetRegistry__InvalidMetadataProvider();
////////////////////////////////////////////////////////////////////////////
// IPResolver ///
////////////////////////////////////////////////////////////////////////////
/// @notice The targeted IP does not yet have an IP account.
error IPResolver_InvalidIP();
/// @notice Caller not authorized to perform the IP resolver function call.
error IPResolver_Unauthorized();
////////////////////////////////////////////////////////////////////////////
// Metadata Provider ///
////////////////////////////////////////////////////////////////////////////
/// @notice Provided hash metadata is not valid.
error MetadataProvider__HashInvalid();
/// @notice The caller is not the authorized IP asset owner.
error MetadataProvider__IPAssetOwnerInvalid();
/// @notice Provided hash metadata is not valid.
error MetadataProvider__NameInvalid();
/// @notice The new metadata provider is not compatible with the old provider.
error MetadataProvider__MetadataNotCompatible();
/// @notice Provided registrant metadata is not valid.
error MetadataProvider__RegistrantInvalid();
/// @notice Provided registration date is not valid.
error MetadataProvider__RegistrationDateInvalid();
/// @notice Caller does not access to set metadata storage for the provider.
error MetadataProvider__Unauthorized();
/// @notice A metadata provider upgrade is not currently available.
error MetadataProvider__UpgradeUnavailable();
/// @notice The upgrade provider is not valid.
error MetadataProvider__UpgradeProviderInvalid();
/// @notice Provided metadata URI is not valid.
error MetadataProvider__URIInvalid();
////////////////////////////////////////////////////////////////////////////
// LicenseRegistry //
////////////////////////////////////////////////////////////////////////////
error LicenseRegistry__CallerNotLicensingModule();
error LicenseRegistry__ZeroLicensingModule();
error LicensingModule__CallerNotLicenseRegistry();
error LicenseRegistry__RevokedLicense();
/// @notice emitted when trying to transfer a license that is not transferable (by policy)
error LicenseRegistry__NotTransferable();
/// @notice emitted on constructor if dispute module is not set
error LicenseRegistry__ZeroDisputeModule();
////////////////////////////////////////////////////////////////////////////
// LicensingModule //
////////////////////////////////////////////////////////////////////////////
error LicensingModule__PolicyAlreadySetForIpId();
error LicensingModule__FrameworkNotFound();
error LicensingModule__EmptyLicenseUrl();
error LicensingModule__InvalidPolicyFramework();
error LicensingModule__ParamVerifierLengthMismatch();
error LicensingModule__PolicyNotFound();
error LicensingModule__NotLicensee();
error LicensingModule__ParentIdEqualThanChild();
error LicensingModule__LicensorDoesntHaveThisPolicy();
error LicensingModule__MintLicenseParamFailed();
error LicensingModule__LinkParentParamFailed();
error LicensingModule__TransferParamFailed();
error LicensingModule__InvalidLicensor();
error LicensingModule__ParamVerifierAlreadySet();
error LicensingModule__CommercialTermInNonCommercialPolicy();
error LicensingModule__EmptyParamName();
error LicensingModule__UnregisteredFrameworkAddingPolicy();
error LicensingModule__UnauthorizedAccess();
error LicensingModule__LicensorNotRegistered();
error LicensingModule__CallerNotLicensorAndPolicyNotSet();
error LicensingModule__DerivativesCannotAddPolicy();
error LicensingModule__IncompatibleRoyaltyPolicyAddress();
error LicensingModule__IncompatibleRoyaltyPolicyDerivativeRevShare();
error LicensingModule__IncompatibleLicensorCommercialPolicy();
error LicensingModule__IncompatibleLicensorRoyaltyDerivativeRevShare();
error LicensingModule__DerivativeRevShareSumExceedsMaxRNFTSupply();
error LicensingModule__MismatchBetweenRoyaltyPolicy();
error LicensingModule__RegisterPolicyFrameworkMismatch();
error LicensingModule__RoyaltyPolicyNotWhitelisted();
error LicensingModule__MintingFeeTokenNotWhitelisted();
error LicensingModule__ReceiverZeroAddress();
error LicensingModule__MintAmountZero();
/// @notice emitted when trying to interact with an IP that has been disputed in the DisputeModule
error LicensingModule__DisputedIpId();
/// @notice emitted when linking a license from a licensor that has been disputed in the DisputeModule
error LicensingModule__LinkingRevokedLicense();
////////////////////////////////////////////////////////////////////////////
// LicensingModuleAware //
////////////////////////////////////////////////////////////////////////////
error LicensingModuleAware__CallerNotLicensingModule();
////////////////////////////////////////////////////////////////////////////
// PolicyFrameworkManager //
////////////////////////////////////////////////////////////////////////////
error PolicyFrameworkManager__GettingPolicyWrongFramework();
error PolicyFrameworkManager__CommercializerCheckerDoesNotSupportHook(address commercializer);
////////////////////////////////////////////////////////////////////////////
// LicensorApprovalChecker //
////////////////////////////////////////////////////////////////////////////
error LicensorApprovalChecker__Unauthorized();
////////////////////////////////////////////////////////////////////////////
// Dispute Module //
////////////////////////////////////////////////////////////////////////////
error DisputeModule__ZeroArbitrationPolicy();
error DisputeModule__ZeroArbitrationRelayer();
error DisputeModule__ZeroDisputeTag();
error DisputeModule__ZeroLinkToDisputeEvidence();
error DisputeModule__NotWhitelistedArbitrationPolicy();
error DisputeModule__NotWhitelistedDisputeTag();
error DisputeModule__NotWhitelistedArbitrationRelayer();
error DisputeModule__NotDisputeInitiator();
error DisputeModule__NotInDisputeState();
error DisputeModule__NotAbleToResolve();
error DisputeModule__NotRegisteredIpId();
error DisputeModule__UnauthorizedAccess();
error ArbitrationPolicySP__ZeroDisputeModule();
error ArbitrationPolicySP__ZeroPaymentToken();
error ArbitrationPolicySP__NotDisputeModule();
////////////////////////////////////////////////////////////////////////////
// Royalty Module //
////////////////////////////////////////////////////////////////////////////
error RoyaltyModule__ZeroRoyaltyPolicy();
error RoyaltyModule__NotWhitelistedRoyaltyPolicy();
error RoyaltyModule__ZeroRoyaltyToken();
error RoyaltyModule__NotWhitelistedRoyaltyToken();
error RoyaltyModule__NoRoyaltyPolicySet();
error RoyaltyModule__IncompatibleRoyaltyPolicy();
error RoyaltyModule__NotAllowedCaller();
error RoyaltyModule__ZeroLicensingModule();
error RoyaltyModule__CanOnlyMintSelectedPolicy();
error RoyaltyModule__NoParentsOnLinking();
error RoyaltyModule__NotRegisteredIpId();
error RoyaltyPolicyLAP__ZeroRoyaltyModule();
error RoyaltyPolicyLAP__ZeroLiquidSplitFactory();
error RoyaltyPolicyLAP__ZeroLiquidSplitMain();
error RoyaltyPolicyLAP__NotRoyaltyModule();
error RoyaltyPolicyLAP__ZeroLicensingModule();
error RoyaltyPolicyLAP__AboveParentLimit();
error RoyaltyPolicyLAP__AboveAncestorsLimit();
error RoyaltyPolicyLAP__AboveRoyaltyStackLimit();
error RoyaltyPolicyLAP__InvalidAncestorsLength();
error RoyaltyPolicyLAP__InvalidAncestors();
error RoyaltyPolicyLAP__InvalidRoyaltyAmountLength();
error RoyaltyPolicyLAP__InvalidAncestorsHash();
error RoyaltyPolicyLAP__InvalidParentRoyaltiesLength();
error RoyaltyPolicyLAP__InvalidAncestorsRoyalty();
error RoyaltyPolicyLAP__ImplementationAlreadySet();
error RoyaltyPolicyLAP__ZeroAncestorsVaultImpl();
error RoyaltyPolicyLAP__NotFullOwnership();
error RoyaltyPolicyLAP__UnlinkableToParents();
error RoyaltyPolicyLAP__TransferFailed();
error RoyaltyPolicyLAP__LastPositionNotAbleToMintLicense();
error AncestorsVaultLAP__ZeroRoyaltyPolicyLAP();
error AncestorsVaultLAP__AlreadyClaimed();
error AncestorsVaultLAP__InvalidAncestorsHash();
error AncestorsVaultLAP__InvalidClaimer();
error AncestorsVaultLAP__ClaimerNotAnAncestor();
error AncestorsVaultLAP__ETHBalanceNotZero();
error AncestorsVaultLAP__ERC20BalanceNotZero();
error AncestorsVaultLAP__TransferFailed();
////////////////////////////////////////////////////////////////////////////
// ModuleRegistry //
////////////////////////////////////////////////////////////////////////////
error ModuleRegistry__ModuleAddressZeroAddress();
error ModuleRegistry__ModuleAddressNotContract();
error ModuleRegistry__ModuleAlreadyRegistered();
error ModuleRegistry__NameEmptyString();
error ModuleRegistry__NameAlreadyRegistered();
error ModuleRegistry__NameDoesNotMatch();
error ModuleRegistry__ModuleNotRegistered();
error ModuleRegistry__InterfaceIdZero();
error ModuleRegistry__ModuleTypeAlreadyRegistered();
error ModuleRegistry__ModuleTypeNotRegistered();
error ModuleRegistry__ModuleNotSupportExpectedModuleTypeInterfaceId();
error ModuleRegistry__ModuleTypeEmptyString();
////////////////////////////////////////////////////////////////////////////
// RegistrationModule //
////////////////////////////////////////////////////////////////////////////
/// @notice The caller is not the owner of the root IP NFT.
error RegistrationModule__InvalidOwner();
////////////////////////////////////////////////////////////////////////////
// AccessController //
////////////////////////////////////////////////////////////////////////////
error AccessController__IPAccountIsZeroAddress();
error AccessController__IPAccountIsNotValid(address ipAccount);
error AccessController__SignerIsZeroAddress();
error AccessController__CallerIsNotIPAccount();
error AccessController__PermissionIsNotValid();
error AccessController__BothCallerAndRecipientAreNotRegisteredModule(address signer, address to);
error AccessController__PermissionDenied(address ipAccount, address signer, address to, bytes4 func);
////////////////////////////////////////////////////////////////////////////
// AccessControlled //
////////////////////////////////////////////////////////////////////////////
error AccessControlled__ZeroAddress();
error AccessControlled__NotIpAccount(address ipAccount);
error AccessControlled__CallerIsNotIpAccount(address caller);
}// 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: BUSL-1.1
pragma solidity 0.8.23;
/// @title Access Permission Library
/// @notice Library for IPAccount access control permissions.
/// These permissions are used by the AccessController.
library AccessPermission {
/// @notice ABSTAIN means having not enough information to make decision at current level, deferred decision to up
/// level permission.
uint8 public constant ABSTAIN = 0;
/// @notice ALLOW means the permission is granted to transaction signer to call the function.
uint8 public constant ALLOW = 1;
/// @notice DENY means the permission is denied to transaction signer to call the function.
uint8 public constant DENY = 2;
/// @notice This struct is used to represent permissions in batch operations within the AccessController.
/// @param ipAccount The address of the IP account that grants the permission for `signer`
/// @param signer The address that can call `to` on behalf of the `ipAccount`
/// @param to The address that can be called by the `signer` (currently only modules can be `to`)
/// @param func The function selector of `to` that can be called by the `signer` on behalf of the `ipAccount`
/// @param permission The permission level for the transaction (0 = ABSTAIN, 1 = ALLOW, 2 = DENY).
struct Permission {
address ipAccount;
address signer;
address to;
bytes4 func;
uint8 permission;
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/introspection/ERC165Checker.sol)
pragma solidity ^0.8.20;
import {IERC165} from "./IERC165.sol";
/**
* @dev Library used to query support of an interface declared via {IERC165}.
*
* Note that these functions return the actual result of the query: they do not
* `revert` if an interface is not supported. It is up to the caller to decide
* what to do in these cases.
*/
library ERC165Checker {
// As per the EIP-165 spec, no interface should ever match 0xffffffff
bytes4 private constant INTERFACE_ID_INVALID = 0xffffffff;
/**
* @dev Returns true if `account` supports the {IERC165} interface.
*/
function supportsERC165(address account) internal view returns (bool) {
// Any contract that implements ERC165 must explicitly indicate support of
// InterfaceId_ERC165 and explicitly indicate non-support of InterfaceId_Invalid
return
supportsERC165InterfaceUnchecked(account, type(IERC165).interfaceId) &&
!supportsERC165InterfaceUnchecked(account, INTERFACE_ID_INVALID);
}
/**
* @dev Returns true if `account` supports the interface defined by
* `interfaceId`. Support for {IERC165} itself is queried automatically.
*
* See {IERC165-supportsInterface}.
*/
function supportsInterface(address account, bytes4 interfaceId) internal view returns (bool) {
// query support of both ERC165 as per the spec and support of _interfaceId
return supportsERC165(account) && supportsERC165InterfaceUnchecked(account, interfaceId);
}
/**
* @dev Returns a boolean array where each value corresponds to the
* interfaces passed in and whether they're supported or not. This allows
* you to batch check interfaces for a contract where your expectation
* is that some interfaces may not be supported.
*
* See {IERC165-supportsInterface}.
*/
function getSupportedInterfaces(
address account,
bytes4[] memory interfaceIds
) internal view returns (bool[] memory) {
// an array of booleans corresponding to interfaceIds and whether they're supported or not
bool[] memory interfaceIdsSupported = new bool[](interfaceIds.length);
// query support of ERC165 itself
if (supportsERC165(account)) {
// query support of each interface in interfaceIds
for (uint256 i = 0; i < interfaceIds.length; i++) {
interfaceIdsSupported[i] = supportsERC165InterfaceUnchecked(account, interfaceIds[i]);
}
}
return interfaceIdsSupported;
}
/**
* @dev Returns true if `account` supports all the interfaces defined in
* `interfaceIds`. Support for {IERC165} itself is queried automatically.
*
* Batch-querying can lead to gas savings by skipping repeated checks for
* {IERC165} support.
*
* See {IERC165-supportsInterface}.
*/
function supportsAllInterfaces(address account, bytes4[] memory interfaceIds) internal view returns (bool) {
// query support of ERC165 itself
if (!supportsERC165(account)) {
return false;
}
// query support of each interface in interfaceIds
for (uint256 i = 0; i < interfaceIds.length; i++) {
if (!supportsERC165InterfaceUnchecked(account, interfaceIds[i])) {
return false;
}
}
// all interfaces supported
return true;
}
/**
* @notice Query if a contract implements an interface, does not check ERC165 support
* @param account The address of the contract to query for support of an interface
* @param interfaceId The interface identifier, as specified in ERC-165
* @return true if the contract at account indicates support of the interface with
* identifier interfaceId, false otherwise
* @dev Assumes that account contains a contract that supports ERC165, otherwise
* the behavior of this method is undefined. This precondition can be checked
* with {supportsERC165}.
*
* Some precompiled contracts will falsely indicate support for a given interface, so caution
* should be exercised when using this function.
*
* Interface identification is specified in ERC-165.
*/
function supportsERC165InterfaceUnchecked(address account, bytes4 interfaceId) internal view returns (bool) {
// prepare call
bytes memory encodedParams = abi.encodeCall(IERC165.supportsInterface, (interfaceId));
// perform static call
bool success;
uint256 returnSize;
uint256 returnValue;
assembly {
success := staticcall(30000, account, add(encodedParams, 0x20), mload(encodedParams), 0x00, 0x20)
returnSize := returndatasize()
returnValue := mload(0x00)
}
return success && returnSize >= 0x20 && returnValue > 0;
}
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
/// @dev the ERC-165 identifier for this interface is `0x6faff5f1`
interface IERC6551Account {
/**
* @dev Allows the account to receive Ether.
*
* Accounts MUST implement a `receive` function.
*
* Accounts MAY perform arbitrary logic to restrict conditions
* under which Ether can be received.
*/
receive() external payable;
/**
* @dev Returns the identifier of the non-fungible token which owns the account.
*
* The return value of this function MUST be constant - it MUST NOT change over time.
*
* @return chainId The EIP-155 ID of the chain the token exists on
* @return tokenContract The contract address of the token
* @return tokenId The ID of the token
*/
function token()
external
view
returns (uint256 chainId, address tokenContract, uint256 tokenId);
/**
* @dev Returns a value that SHOULD be modified each time the account changes state.
*
* @return The current account state
*/
function state() external view returns (uint256);
/**
* @dev Returns a magic value indicating whether a given signer is authorized to act on behalf
* of the account.
*
* MUST return the bytes4 magic value 0x523e3260 if the given signer is valid.
*
* By default, the holder of the non-fungible token the account is bound to MUST be considered
* a valid signer.
*
* Accounts MAY implement additional authorization logic which invalidates the holder as a
* signer or grants signing permissions to other non-holder accounts.
*
* @param signer The address to check signing authorization for
* @param context Additional data used to determine whether the signer is valid
* @return magicValue Magic value indicating whether the signer is valid
*/
function isValidSigner(address signer, bytes calldata context)
external
view
returns (bytes4 magicValue);
}// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.23;
import { IERC721Receiver } from "@openzeppelin/contracts/token/ERC721/IERC721Receiver.sol";
import { IERC1155Receiver } from "@openzeppelin/contracts/token/ERC1155/IERC1155Receiver.sol";
import { IERC6551Account } from "erc6551/interfaces/IERC6551Account.sol";
/// @title IIPAccount
/// @dev IPAccount is a token-bound account that adopts the EIP-6551 standard.
/// These accounts are deployed at deterministic addresses through the official 6551 account registry.
/// As a deployed smart contract, IPAccount can store IP-related information,
/// like ownership of other NFTs such as license NFT or Royalty NFT.
/// IPAccount can interact with modules by making calls as a normal transaction sender.
/// This allows for seamless operations on the state and data of IP.
/// IPAccount is core identity for all actions.
interface IIPAccount is IERC6551Account, IERC721Receiver, IERC1155Receiver {
/// @notice Emitted when a transaction is executed.
/// @param to The recipient of the transaction.
/// @param value The amount of Ether sent.
/// @param data The data sent along with the transaction.
/// @param nonce The nonce of the transaction.
event Executed(address indexed to, uint256 value, bytes data, uint256 nonce);
/// @notice Emitted when a transaction is executed on behalf of the signer.
/// @param to The recipient of the transaction.
/// @param value The amount of Ether sent.
/// @param data The data sent along with the transaction.
/// @param nonce The nonce of the transaction.
/// @param deadline The deadline of the transaction signature.
/// @param signer The signer of the transaction.
/// @param signature The signature of the transaction, EIP-712 encoded.
event ExecutedWithSig(
address indexed to,
uint256 value,
bytes data,
uint256 nonce,
uint256 deadline,
address indexed signer,
bytes signature
);
/// @notice Returns the IPAccount's internal nonce for transaction ordering.
function state() external view returns (uint256);
/// @notice Returns the identifier of the non-fungible token which owns the account
/// @return chainId The EIP-155 ID of the chain the token exists on
/// @return tokenContract The contract address of the token
/// @return tokenId The ID of the token
function token() external view returns (uint256, address, uint256);
/// @notice Checks if the signer is valid for the given data
/// @param signer The signer to check
/// @param data The data to check against
/// @return The function selector if the signer is valid, 0 otherwise
function isValidSigner(address signer, bytes calldata data) external view returns (bytes4);
/// @notice Returns the owner of the IP Account.
/// @return owner The address of the owner.
function owner() external view returns (address);
/// @notice Executes a transaction from the IP Account on behalf of the signer.
/// @param to The recipient of the transaction.
/// @param value The amount of Ether to send.
/// @param data The data to send along with the transaction.
/// @param signer The signer of the transaction.
/// @param deadline The deadline of the transaction signature.
/// @param signature The signature of the transaction, EIP-712 encoded.
/// @return result The return data from the transaction.
function executeWithSig(
address to,
uint256 value,
bytes calldata data,
address signer,
uint256 deadline,
bytes calldata signature
) external payable returns (bytes memory);
/// @notice Executes a transaction from the IP Account.
/// @param to The recipient of the transaction.
/// @param value The amount of Ether to send.
/// @param data The data to send along with the transaction.
/// @return result The return data from the transaction.
function execute(address to, uint256 value, bytes calldata data) external payable returns (bytes memory);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (token/ERC721/IERC721Receiver.sol)
pragma solidity ^0.8.20;
/**
* @title ERC721 token receiver interface
* @dev Interface for any contract that wants to support safeTransfers
* from ERC721 asset contracts.
*/
interface IERC721Receiver {
/**
* @dev Whenever an {IERC721} `tokenId` token is transferred to this contract via {IERC721-safeTransferFrom}
* by `operator` from `from`, this function is called.
*
* It must return its Solidity selector to confirm the token transfer.
* If any other value is returned or the interface is not implemented by the recipient, the transfer will be
* reverted.
*
* The selector can be obtained in Solidity with `IERC721Receiver.onERC721Received.selector`.
*/
function onERC721Received(
address operator,
address from,
uint256 tokenId,
bytes calldata data
) external returns (bytes4);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (token/ERC1155/IERC1155Receiver.sol)
pragma solidity ^0.8.20;
import {IERC165} from "../../utils/introspection/IERC165.sol";
/**
* @dev Interface that must be implemented by smart contracts in order to receive
* ERC-1155 token transfers.
*/
interface IERC1155Receiver is IERC165 {
/**
* @dev Handles the receipt of a single ERC1155 token type. This function is
* called at the end of a `safeTransferFrom` after the balance has been updated.
*
* NOTE: To accept the transfer, this must return
* `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))`
* (i.e. 0xf23a6e61, or its own function selector).
*
* @param operator The address which initiated the transfer (i.e. msg.sender)
* @param from The address which previously owned the token
* @param id The ID of the token being transferred
* @param value The amount of tokens being transferred
* @param data Additional data with no specified format
* @return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` if transfer is allowed
*/
function onERC1155Received(
address operator,
address from,
uint256 id,
uint256 value,
bytes calldata data
) external returns (bytes4);
/**
* @dev Handles the receipt of a multiple ERC1155 token types. This function
* is called at the end of a `safeBatchTransferFrom` after the balances have
* been updated.
*
* NOTE: To accept the transfer(s), this must return
* `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))`
* (i.e. 0xbc197c81, or its own function selector).
*
* @param operator The address which initiated the batch transfer (i.e. msg.sender)
* @param from The address which previously owned the token
* @param ids An array containing ids of each token being transferred (order and length must match values array)
* @param values An array containing amounts of each token being transferred (order and length must match ids array)
* @param data Additional data with no specified format
* @return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` if transfer is allowed
*/
function onERC1155BatchReceived(
address operator,
address from,
uint256[] calldata ids,
uint256[] calldata values,
bytes calldata data
) external returns (bytes4);
}{
"remappings": [
"@ethereum-waffle/=node_modules/@ethereum-waffle/",
"@openzeppelin/=node_modules/@openzeppelin/",
"forge-std/=node_modules/forge-std/src/",
"ds-test/=node_modules/ds-test/src/",
"base64-sol/=node_modules/base64-sol/",
"eth-gas-reporter/=node_modules/eth-gas-reporter/",
"hardhat-deploy/=node_modules/hardhat-deploy/",
"hardhat/=node_modules/hardhat/",
"erc6551/=node_modules/erc6551/",
"openzeppelin-contracts/=lib/reference/lib/openzeppelin-contracts/",
"reference/=lib/reference/"
],
"optimizer": {
"enabled": true,
"runs": 20000
},
"metadata": {
"useLiteralContent": false,
"bytecodeHash": "ipfs",
"appendCBOR": true
},
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
},
"evmVersion": "paris",
"libraries": {
"contracts/lib/registries/IPAccountChecker.sol": {
"IPAccountChecker": "0x36e93affeca875ebcef53e922a4b716ad2a508a9"
}
}
}Contract ABI
API[{"inputs":[{"internalType":"address","name":"accessController","type":"address"},{"internalType":"address","name":"ipAssetRegistry","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[{"internalType":"address","name":"ipAccount","type":"address"}],"name":"AccessControlled__NotIpAccount","type":"error"},{"inputs":[],"name":"AccessControlled__ZeroAddress","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"ipId","type":"address"},{"indexed":true,"internalType":"string","name":"key","type":"string"},{"indexed":false,"internalType":"string","name":"value","type":"string"}],"name":"KeyValueSet","type":"event"},{"inputs":[],"name":"ACCESS_CONTROLLER","outputs":[{"internalType":"contract IAccessController","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"IP_ACCOUNT_REGISTRY","outputs":[{"internalType":"contract IIPAccountRegistry","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"ipId","type":"address"},{"internalType":"string","name":"key","type":"string"},{"internalType":"string","name":"val","type":"string"}],"name":"setValue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"id","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"ipId","type":"address"},{"internalType":"string","name":"key","type":"string"}],"name":"value","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"}]Contract Creation Code
60c060405234801561001057600080fd5b50604051610c77380380610c7783398101604081905261002f916100b9565b818181816001600160a01b03821661005a576040516320a816ad60e01b815260040160405180910390fd5b6001600160a01b038116610081576040516320a816ad60e01b815260040160405180910390fd5b6001600160a01b039182166080521660a052506100ec92505050565b80516001600160a01b03811681146100b457600080fd5b919050565b600080604083850312156100cc57600080fd5b6100d58361009d565b91506100e36020840161009d565b90509250929050565b60805160a051610b5861011f6000396000818161014c01526103fd01526000818161010001526105740152610b586000f3fe608060405234801561001057600080fd5b50600436106100725760003560e01c80631b8b1073116100505780631b8b1073146100fb578063702acd8514610147578063dd75fb631461016e57600080fd5b806301ffc9a71461007757806306fdde031461009f57806314ee889e146100e8575b600080fd5b61008a6100853660046106ba565b610183565b60405190151581526020015b60405180910390f35b6100db6040518060400160405280601281526020017f49505f5245534f4c5645525f4d4f44554c45000000000000000000000000000081525081565b6040516100969190610703565b6100db6100f63660046107e2565b610194565b6101227f000000000000000000000000000000000000000000000000000000000000000081565b60405173ffffffffffffffffffffffffffffffffffffffff9091168152602001610096565b6101227f000000000000000000000000000000000000000000000000000000000000000081565b61018161017c366004610835565b610284565b005b600061018e8261036a565b92915050565b60606000808573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002083836040516101e49291906108b6565b908152602001604051809103902080546101fd906108c6565b80601f0160208091040260200160405190810160405280929190818152602001828054610229906108c6565b80156102765780601f1061024b57610100808354040283529160200191610276565b820191906000526020600020905b81548152906001019060200180831161025957829003601f168201915b505050505090509392505050565b8461028e816103c0565b82826000808973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002087876040516102de9291906108b6565b908152602001604051809103902091826102f9929190610999565b50848460405161030a9291906108b6565b60405180910390208673ffffffffffffffffffffffffffffffffffffffff167fce95ee68edc437f1ab7d39e82f77edcaf8434d037c4c44bcf686e1b377bb7e95858560405161035a929190610ab3565b60405180910390a3505050505050565b60007fffffffff0000000000000000000000000000000000000000000000000000000082167fc99b73fd00000000000000000000000000000000000000000000000000000000148061018e575061018e826105d2565b6040517f5a1c2dd700000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff7f000000000000000000000000000000000000000000000000000000000000000081166004830152821660248201527336e93affeca875ebcef53e922a4b716ad2a508a990635a1c2dd790604401602060405180830381865af4158015610466573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061048a9190610b00565b6104dc576040517fd64edf9000000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff8216600482015260240160405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff8216146105cf576040517f7dfd0ddb00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82811660048301523360248301523060448301526000357fffffffff000000000000000000000000000000000000000000000000000000001660648301527f00000000000000000000000000000000000000000000000000000000000000001690637dfd0ddb9060840160006040518083038186803b1580156105b657600080fd5b505afa1580156105ca573d6000803e3d6000fd5b505050505b50565b60007fffffffff0000000000000000000000000000000000000000000000000000000082167f01ffc9a700000000000000000000000000000000000000000000000000000000148061018e575061018e8260007fffffffff0000000000000000000000000000000000000000000000000000000082167f06fdde0300000000000000000000000000000000000000000000000000000000148061018e57507f01ffc9a7000000000000000000000000000000000000000000000000000000007fffffffff0000000000000000000000000000000000000000000000000000000083161461018e565b6000602082840312156106cc57600080fd5b81357fffffffff00000000000000000000000000000000000000000000000000000000811681146106fc57600080fd5b9392505050565b60006020808352835180602085015260005b8181101561073157858101830151858201604001528201610715565b5060006040828601015260407fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0601f8301168501019250505092915050565b803573ffffffffffffffffffffffffffffffffffffffff8116811461079457600080fd5b919050565b60008083601f8401126107ab57600080fd5b50813567ffffffffffffffff8111156107c357600080fd5b6020830191508360208285010111156107db57600080fd5b9250929050565b6000806000604084860312156107f757600080fd5b61080084610770565b9250602084013567ffffffffffffffff81111561081c57600080fd5b61082886828701610799565b9497909650939450505050565b60008060008060006060868803121561084d57600080fd5b61085686610770565b9450602086013567ffffffffffffffff8082111561087357600080fd5b61087f89838a01610799565b9096509450604088013591508082111561089857600080fd5b506108a588828901610799565b969995985093965092949392505050565b8183823760009101908152919050565b600181811c908216806108da57607f821691505b602082108103610913577f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b50919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b601f821115610994576000816000526020600020601f850160051c810160208610156109715750805b601f850160051c820191505b818110156109905782815560010161097d565b5050505b505050565b67ffffffffffffffff8311156109b1576109b1610919565b6109c5836109bf83546108c6565b83610948565b6000601f841160018114610a1757600085156109e15750838201355b7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600387901b1c1916600186901b1783556105ca565b6000838152602090207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0861690835b82811015610a665786850135825560209485019460019092019101610a46565b5086821015610aa1577fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff60f88860031b161c19848701351681555b505060018560011b0183555050505050565b60208152816020820152818360408301376000818301604090810191909152601f9092017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0160101919050565b600060208284031215610b1257600080fd5b815180151581146106fc57600080fdfea264697066735822122033cc93c1a1626ee15f09846b0f9a917ec3f91b676b912317496b0d2da699634864736f6c63430008170033000000000000000000000000ad64a4b2e18ff7d2f97af083e7b193d7dd141735000000000000000000000000292639452a975630802c17c9267169d93bd5a793
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106100725760003560e01c80631b8b1073116100505780631b8b1073146100fb578063702acd8514610147578063dd75fb631461016e57600080fd5b806301ffc9a71461007757806306fdde031461009f57806314ee889e146100e8575b600080fd5b61008a6100853660046106ba565b610183565b60405190151581526020015b60405180910390f35b6100db6040518060400160405280601281526020017f49505f5245534f4c5645525f4d4f44554c45000000000000000000000000000081525081565b6040516100969190610703565b6100db6100f63660046107e2565b610194565b6101227f000000000000000000000000ad64a4b2e18ff7d2f97af083e7b193d7dd14173581565b60405173ffffffffffffffffffffffffffffffffffffffff9091168152602001610096565b6101227f000000000000000000000000292639452a975630802c17c9267169d93bd5a79381565b61018161017c366004610835565b610284565b005b600061018e8261036a565b92915050565b60606000808573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002083836040516101e49291906108b6565b908152602001604051809103902080546101fd906108c6565b80601f0160208091040260200160405190810160405280929190818152602001828054610229906108c6565b80156102765780601f1061024b57610100808354040283529160200191610276565b820191906000526020600020905b81548152906001019060200180831161025957829003601f168201915b505050505090509392505050565b8461028e816103c0565b82826000808973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002087876040516102de9291906108b6565b908152602001604051809103902091826102f9929190610999565b50848460405161030a9291906108b6565b60405180910390208673ffffffffffffffffffffffffffffffffffffffff167fce95ee68edc437f1ab7d39e82f77edcaf8434d037c4c44bcf686e1b377bb7e95858560405161035a929190610ab3565b60405180910390a3505050505050565b60007fffffffff0000000000000000000000000000000000000000000000000000000082167fc99b73fd00000000000000000000000000000000000000000000000000000000148061018e575061018e826105d2565b6040517f5a1c2dd700000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff7f000000000000000000000000292639452a975630802c17c9267169d93bd5a79381166004830152821660248201527336e93affeca875ebcef53e922a4b716ad2a508a990635a1c2dd790604401602060405180830381865af4158015610466573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061048a9190610b00565b6104dc576040517fd64edf9000000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff8216600482015260240160405180910390fd5b3373ffffffffffffffffffffffffffffffffffffffff8216146105cf576040517f7dfd0ddb00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82811660048301523360248301523060448301526000357fffffffff000000000000000000000000000000000000000000000000000000001660648301527f000000000000000000000000ad64a4b2e18ff7d2f97af083e7b193d7dd1417351690637dfd0ddb9060840160006040518083038186803b1580156105b657600080fd5b505afa1580156105ca573d6000803e3d6000fd5b505050505b50565b60007fffffffff0000000000000000000000000000000000000000000000000000000082167f01ffc9a700000000000000000000000000000000000000000000000000000000148061018e575061018e8260007fffffffff0000000000000000000000000000000000000000000000000000000082167f06fdde0300000000000000000000000000000000000000000000000000000000148061018e57507f01ffc9a7000000000000000000000000000000000000000000000000000000007fffffffff0000000000000000000000000000000000000000000000000000000083161461018e565b6000602082840312156106cc57600080fd5b81357fffffffff00000000000000000000000000000000000000000000000000000000811681146106fc57600080fd5b9392505050565b60006020808352835180602085015260005b8181101561073157858101830151858201604001528201610715565b5060006040828601015260407fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0601f8301168501019250505092915050565b803573ffffffffffffffffffffffffffffffffffffffff8116811461079457600080fd5b919050565b60008083601f8401126107ab57600080fd5b50813567ffffffffffffffff8111156107c357600080fd5b6020830191508360208285010111156107db57600080fd5b9250929050565b6000806000604084860312156107f757600080fd5b61080084610770565b9250602084013567ffffffffffffffff81111561081c57600080fd5b61082886828701610799565b9497909650939450505050565b60008060008060006060868803121561084d57600080fd5b61085686610770565b9450602086013567ffffffffffffffff8082111561087357600080fd5b61087f89838a01610799565b9096509450604088013591508082111561089857600080fd5b506108a588828901610799565b969995985093965092949392505050565b8183823760009101908152919050565b600181811c908216806108da57607f821691505b602082108103610913577f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b50919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b601f821115610994576000816000526020600020601f850160051c810160208610156109715750805b601f850160051c820191505b818110156109905782815560010161097d565b5050505b505050565b67ffffffffffffffff8311156109b1576109b1610919565b6109c5836109bf83546108c6565b83610948565b6000601f841160018114610a1757600085156109e15750838201355b7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600387901b1c1916600186901b1783556105ca565b6000838152602090207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0861690835b82811015610a665786850135825560209485019460019092019101610a46565b5086821015610aa1577fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff60f88860031b161c19848701351681555b505060018560011b0183555050505050565b60208152816020820152818360408301376000818301604090810191909152601f9092017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0160101919050565b600060208284031215610b1257600080fd5b815180151581146106fc57600080fdfea264697066735822122033cc93c1a1626ee15f09846b0f9a917ec3f91b676b912317496b0d2da699634864736f6c63430008170033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
000000000000000000000000ad64a4b2e18ff7d2f97af083e7b193d7dd141735000000000000000000000000292639452a975630802c17c9267169d93bd5a793
-----Decoded View---------------
Arg [0] : accessController (address): 0xad64a4b2e18FF7D2f97aF083E7b193d7Dd141735
Arg [1] : ipAssetRegistry (address): 0x292639452A975630802C17c9267169D93BD5a793
-----Encoded View---------------
2 Constructor Arguments found :
Arg [0] : 000000000000000000000000ad64a4b2e18ff7d2f97af083e7b193d7dd141735
Arg [1] : 000000000000000000000000292639452a975630802c17c9267169d93bd5a793
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ 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.