Source Code
Overview
ETH Balance
0 ETH
ETH Value
$0.00Multichain Info
N/A
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Cross-Chain Transactions
Loading...
Loading
Contract Name:
Mailbox
Compiler Version
v0.8.22+commit.4fc1097e
Optimization Enabled:
Yes with 999999 runs
Other Settings:
paris EvmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.8.0;
// ============ Internal Imports ============
import {Versioned} from "./upgrade/Versioned.sol";
import {Indexed} from "./libs/Indexed.sol";
import {Message} from "./libs/Message.sol";
import {TypeCasts} from "./libs/TypeCasts.sol";
import {IInterchainSecurityModule, ISpecifiesInterchainSecurityModule} from "./interfaces/IInterchainSecurityModule.sol";
import {IPostDispatchHook} from "./interfaces/hooks/IPostDispatchHook.sol";
import {IMessageRecipient} from "./interfaces/IMessageRecipient.sol";
import {IMailbox} from "./interfaces/IMailbox.sol";
import {PackageVersioned} from "./PackageVersioned.sol";
// ============ External Imports ============
import {Address} from "@openzeppelin/contracts/utils/Address.sol";
import {OwnableUpgradeable} from "@openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol";
contract Mailbox is
IMailbox,
Indexed,
Versioned,
OwnableUpgradeable,
PackageVersioned
{
// ============ Libraries ============
using Message for bytes;
using TypeCasts for bytes32;
using TypeCasts for address;
// ============ Constants ============
// Domain of chain on which the contract is deployed
uint32 public immutable localDomain;
// ============ Public Storage ============
// A monotonically increasing nonce for outbound unique message IDs.
uint32 public nonce;
// The latest dispatched message ID used for auth in post-dispatch hooks.
bytes32 public latestDispatchedId;
// The default ISM, used if the recipient fails to specify one.
IInterchainSecurityModule public defaultIsm;
// The default post dispatch hook, used for post processing of opting-in dispatches.
IPostDispatchHook public defaultHook;
// The required post dispatch hook, used for post processing of ALL dispatches.
IPostDispatchHook public requiredHook;
// Mapping of message ID to delivery context that processed the message.
struct Delivery {
address processor;
uint48 blockNumber;
}
mapping(bytes32 => Delivery) internal deliveries;
// ============ Events ============
/**
* @notice Emitted when the default ISM is updated
* @param module The new default ISM
*/
event DefaultIsmSet(address indexed module);
/**
* @notice Emitted when the default hook is updated
* @param hook The new default hook
*/
event DefaultHookSet(address indexed hook);
/**
* @notice Emitted when the required hook is updated
* @param hook The new required hook
*/
event RequiredHookSet(address indexed hook);
// ============ Constructor ============
constructor(uint32 _localDomain) {
localDomain = _localDomain;
}
// ============ Initializers ============
function initialize(
address _owner,
address _defaultIsm,
address _defaultHook,
address _requiredHook
) external initializer {
__Ownable_init();
setDefaultIsm(_defaultIsm);
setDefaultHook(_defaultHook);
setRequiredHook(_requiredHook);
transferOwnership(_owner);
}
// ============ External Functions ============
/**
* @notice Dispatches a message to the destination domain & recipient
* using the default hook and empty metadata.
* @param _destinationDomain Domain of destination chain
* @param _recipientAddress Address of recipient on destination chain as bytes32
* @param _messageBody Raw bytes content of message body
* @return The message ID inserted into the Mailbox's merkle tree
*/
function dispatch(
uint32 _destinationDomain,
bytes32 _recipientAddress,
bytes calldata _messageBody
) external payable override returns (bytes32) {
return
dispatch(
_destinationDomain,
_recipientAddress,
_messageBody,
_messageBody[0:0],
defaultHook
);
}
/**
* @notice Dispatches a message to the destination domain & recipient.
* @param destinationDomain Domain of destination chain
* @param recipientAddress Address of recipient on destination chain as bytes32
* @param messageBody Raw bytes content of message body
* @param hookMetadata Metadata used by the post dispatch hook
* @return The message ID inserted into the Mailbox's merkle tree
*/
function dispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata hookMetadata
) external payable override returns (bytes32) {
return
dispatch(
destinationDomain,
recipientAddress,
messageBody,
hookMetadata,
defaultHook
);
}
/**
* @notice Computes quote for dipatching a message to the destination domain & recipient
* using the default hook and empty metadata.
* @param destinationDomain Domain of destination chain
* @param recipientAddress Address of recipient on destination chain as bytes32
* @param messageBody Raw bytes content of message body
* @return fee The payment required to dispatch the message
*/
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody
) external view returns (uint256 fee) {
return
quoteDispatch(
destinationDomain,
recipientAddress,
messageBody,
messageBody[0:0],
defaultHook
);
}
/**
* @notice Computes quote for dispatching a message to the destination domain & recipient.
* @param destinationDomain Domain of destination chain
* @param recipientAddress Address of recipient on destination chain as bytes32
* @param messageBody Raw bytes content of message body
* @param defaultHookMetadata Metadata used by the default post dispatch hook
* @return fee The payment required to dispatch the message
*/
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata defaultHookMetadata
) external view returns (uint256 fee) {
return
quoteDispatch(
destinationDomain,
recipientAddress,
messageBody,
defaultHookMetadata,
defaultHook
);
}
/**
* @notice Attempts to deliver `_message` to its recipient. Verifies
* `_message` via the recipient's ISM using the provided `_metadata`.
* @param _metadata Metadata used by the ISM to verify `_message`.
* @param _message Formatted Hyperlane message (refer to Message.sol).
*/
function process(
bytes calldata _metadata,
bytes calldata _message
) external payable override {
/// CHECKS ///
// Check that the message was intended for this mailbox.
require(_message.version() == VERSION, "Mailbox: bad version");
require(
_message.destination() == localDomain,
"Mailbox: unexpected destination"
);
// Check that the message hasn't already been delivered.
bytes32 _id = _message.id();
require(delivered(_id) == false, "Mailbox: already delivered");
// Get the recipient's ISM.
address recipient = _message.recipientAddress();
IInterchainSecurityModule ism = recipientIsm(recipient);
/// EFFECTS ///
deliveries[_id] = Delivery({
processor: msg.sender,
blockNumber: uint48(block.number)
});
emit Process(_message.origin(), _message.sender(), recipient);
emit ProcessId(_id);
/// INTERACTIONS ///
// Verify the message via the interchain security module.
require(
ism.verify(_metadata, _message),
"Mailbox: ISM verification failed"
);
// Deliver the message to the recipient.
IMessageRecipient(recipient).handle{value: msg.value}(
_message.origin(),
_message.sender(),
_message.body()
);
}
/**
* @notice Returns the account that processed the message.
* @param _id The message ID to check.
* @return The account that processed the message.
*/
function processor(bytes32 _id) external view returns (address) {
return deliveries[_id].processor;
}
/**
* @notice Returns the account that processed the message.
* @param _id The message ID to check.
* @return The number of the block that the message was processed at.
*/
function processedAt(bytes32 _id) external view returns (uint48) {
return deliveries[_id].blockNumber;
}
// ============ Public Functions ============
/**
* @notice Dispatches a message to the destination domain & recipient.
* @param destinationDomain Domain of destination chain
* @param recipientAddress Address of recipient on destination chain as bytes32
* @param messageBody Raw bytes content of message body
* @param metadata Metadata used by the post dispatch hook
* @param hook Custom hook to use instead of the default
* @return The message ID inserted into the Mailbox's merkle tree
*/
function dispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata metadata,
IPostDispatchHook hook
) public payable virtual returns (bytes32) {
if (address(hook) == address(0)) {
hook = defaultHook;
}
/// CHECKS ///
// Format the message into packed bytes.
bytes memory message = _buildMessage(
destinationDomain,
recipientAddress,
messageBody
);
bytes32 id = message.id();
/// EFFECTS ///
latestDispatchedId = id;
nonce += 1;
emit Dispatch(msg.sender, destinationDomain, recipientAddress, message);
emit DispatchId(id);
/// INTERACTIONS ///
uint256 requiredValue = requiredHook.quoteDispatch(metadata, message);
// if underpaying, defer to required hook's reverting behavior
if (msg.value < requiredValue) {
requiredValue = msg.value;
}
requiredHook.postDispatch{value: requiredValue}(metadata, message);
hook.postDispatch{value: msg.value - requiredValue}(metadata, message);
return id;
}
/**
* @notice Computes quote for dispatching a message to the destination domain & recipient.
* @param destinationDomain Domain of destination chain
* @param recipientAddress Address of recipient on destination chain as bytes32
* @param messageBody Raw bytes content of message body
* @param metadata Metadata used by the post dispatch hook
* @param hook Custom hook to use instead of the default
* @return fee The payment required to dispatch the message
*/
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata metadata,
IPostDispatchHook hook
) public view returns (uint256 fee) {
if (address(hook) == address(0)) {
hook = defaultHook;
}
bytes memory message = _buildMessage(
destinationDomain,
recipientAddress,
messageBody
);
return
requiredHook.quoteDispatch(metadata, message) +
hook.quoteDispatch(metadata, message);
}
/**
* @notice Returns true if the message has been processed.
* @param _id The message ID to check.
* @return True if the message has been delivered.
*/
function delivered(bytes32 _id) public view override returns (bool) {
return deliveries[_id].blockNumber > 0;
}
/**
* @notice Sets the default ISM for the Mailbox.
* @param _module The new default ISM. Must be a contract.
*/
function setDefaultIsm(address _module) public onlyOwner {
require(
Address.isContract(_module),
"Mailbox: default ISM not contract"
);
defaultIsm = IInterchainSecurityModule(_module);
emit DefaultIsmSet(_module);
}
/**
* @notice Sets the default post dispatch hook for the Mailbox.
* @param _hook The new default post dispatch hook. Must be a contract.
*/
function setDefaultHook(address _hook) public onlyOwner {
require(
Address.isContract(_hook),
"Mailbox: default hook not contract"
);
defaultHook = IPostDispatchHook(_hook);
emit DefaultHookSet(_hook);
}
/**
* @notice Sets the required post dispatch hook for the Mailbox.
* @param _hook The new default post dispatch hook. Must be a contract.
*/
function setRequiredHook(address _hook) public onlyOwner {
require(
Address.isContract(_hook),
"Mailbox: required hook not contract"
);
requiredHook = IPostDispatchHook(_hook);
emit RequiredHookSet(_hook);
}
/**
* @notice Returns the ISM to use for the recipient, defaulting to the
* default ISM if none is specified.
* @param _recipient The message recipient whose ISM should be returned.
* @return The ISM to use for `_recipient`.
*/
function recipientIsm(
address _recipient
) public view returns (IInterchainSecurityModule) {
// use low-level staticcall in case of revert or empty return data
(bool success, bytes memory returnData) = _recipient.staticcall(
abi.encodeCall(
ISpecifiesInterchainSecurityModule.interchainSecurityModule,
()
)
);
// check if call was successful and returned data
if (success && returnData.length != 0) {
// check if returnData is a valid address
address ism = abi.decode(returnData, (address));
// check if the ISM is a contract
if (ism != address(0)) {
return IInterchainSecurityModule(ism);
}
}
// Use the default if a valid one is not specified by the recipient.
return defaultIsm;
}
// ============ Internal Functions ============
function _buildMessage(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody
) internal view returns (bytes memory) {
return
Message.formatMessage(
VERSION,
nonce,
localDomain,
msg.sender.addressToBytes32(),
destinationDomain,
recipientAddress,
messageBody
);
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.9.0) (access/Ownable.sol)
pragma solidity ^0.8.0;
import "../utils/ContextUpgradeable.sol";
import "../proxy/utils/Initializable.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.
*
* By default, the owner account will be the one that deploys the contract. 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 OwnableUpgradeable is Initializable, ContextUpgradeable {
address private _owner;
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
/**
* @dev Initializes the contract setting the deployer as the initial owner.
*/
function __Ownable_init() internal onlyInitializing {
__Ownable_init_unchained();
}
function __Ownable_init_unchained() internal onlyInitializing {
_transferOwnership(_msgSender());
}
/**
* @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 {
require(owner() == _msgSender(), "Ownable: caller is not the owner");
}
/**
* @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 {
require(newOwner != address(0), "Ownable: new owner is the zero address");
_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);
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[49] private __gap;
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.9.0) (proxy/utils/Initializable.sol)
pragma solidity ^0.8.2;
import "../../utils/AddressUpgradeable.sol";
/**
* @dev This is a base contract to aid in writing upgradeable contracts, or any kind of contract that will be deployed
* behind a proxy. Since proxied contracts do not make use of a constructor, it's common to move constructor logic to an
* external initializer function, usually called `initialize`. It then becomes necessary to protect this initializer
* function so it can only be called once. The {initializer} modifier provided by this contract will have this effect.
*
* The initialization functions use a version number. Once a version number is used, it is consumed and cannot be
* reused. This mechanism prevents re-execution of each "step" but allows the creation of new initialization steps in
* case an upgrade adds a module that needs to be initialized.
*
* For example:
*
* [.hljs-theme-light.nopadding]
* ```solidity
* contract MyToken is ERC20Upgradeable {
* function initialize() initializer public {
* __ERC20_init("MyToken", "MTK");
* }
* }
*
* contract MyTokenV2 is MyToken, ERC20PermitUpgradeable {
* function initializeV2() reinitializer(2) public {
* __ERC20Permit_init("MyToken");
* }
* }
* ```
*
* TIP: To avoid leaving the proxy in an uninitialized state, the initializer function should be called as early as
* possible by providing the encoded function call as the `_data` argument to {ERC1967Proxy-constructor}.
*
* CAUTION: When used with inheritance, manual care must be taken to not invoke a parent initializer twice, or to ensure
* that all initializers are idempotent. This is not verified automatically as constructors are by Solidity.
*
* [CAUTION]
* ====
* Avoid leaving a contract uninitialized.
*
* An uninitialized contract can be taken over by an attacker. This applies to both a proxy and its implementation
* contract, which may impact the proxy. To prevent the implementation contract from being used, you should invoke
* the {_disableInitializers} function in the constructor to automatically lock it when it is deployed:
*
* [.hljs-theme-light.nopadding]
* ```
* /// @custom:oz-upgrades-unsafe-allow constructor
* constructor() {
* _disableInitializers();
* }
* ```
* ====
*/
abstract contract Initializable {
/**
* @dev Indicates that the contract has been initialized.
* @custom:oz-retyped-from bool
*/
uint8 private _initialized;
/**
* @dev Indicates that the contract is in the process of being initialized.
*/
bool private _initializing;
/**
* @dev Triggered when the contract has been initialized or reinitialized.
*/
event Initialized(uint8 version);
/**
* @dev A modifier that defines a protected initializer function that can be invoked at most once. In its scope,
* `onlyInitializing` functions can be used to initialize parent contracts.
*
* Similar to `reinitializer(1)`, except that functions marked with `initializer` can be nested in the context of a
* constructor.
*
* Emits an {Initialized} event.
*/
modifier initializer() {
bool isTopLevelCall = !_initializing;
require(
(isTopLevelCall && _initialized < 1) || (!AddressUpgradeable.isContract(address(this)) && _initialized == 1),
"Initializable: contract is already initialized"
);
_initialized = 1;
if (isTopLevelCall) {
_initializing = true;
}
_;
if (isTopLevelCall) {
_initializing = false;
emit Initialized(1);
}
}
/**
* @dev A modifier that defines a protected reinitializer function that can be invoked at most once, and only if the
* contract hasn't been initialized to a greater version before. In its scope, `onlyInitializing` functions can be
* used to initialize parent contracts.
*
* A reinitializer may be used after the original initialization step. This is essential to configure modules that
* are added through upgrades and that require initialization.
*
* When `version` is 1, this modifier is similar to `initializer`, except that functions marked with `reinitializer`
* cannot be nested. If one is invoked in the context of another, execution will revert.
*
* Note that versions can jump in increments greater than 1; this implies that if multiple reinitializers coexist in
* a contract, executing them in the right order is up to the developer or operator.
*
* WARNING: setting the version to 255 will prevent any future reinitialization.
*
* Emits an {Initialized} event.
*/
modifier reinitializer(uint8 version) {
require(!_initializing && _initialized < version, "Initializable: contract is already initialized");
_initialized = version;
_initializing = true;
_;
_initializing = false;
emit Initialized(version);
}
/**
* @dev Modifier to protect an initialization function so that it can only be invoked by functions with the
* {initializer} and {reinitializer} modifiers, directly or indirectly.
*/
modifier onlyInitializing() {
require(_initializing, "Initializable: contract is not initializing");
_;
}
/**
* @dev Locks the contract, preventing any future reinitialization. This cannot be part of an initializer call.
* Calling this in the constructor of a contract will prevent that contract from being initialized or reinitialized
* to any version. It is recommended to use this to lock implementation contracts that are designed to be called
* through proxies.
*
* Emits an {Initialized} event the first time it is successfully executed.
*/
function _disableInitializers() internal virtual {
require(!_initializing, "Initializable: contract is initializing");
if (_initialized != type(uint8).max) {
_initialized = type(uint8).max;
emit Initialized(type(uint8).max);
}
}
/**
* @dev Returns the highest version that has been initialized. See {reinitializer}.
*/
function _getInitializedVersion() internal view returns (uint8) {
return _initialized;
}
/**
* @dev Returns `true` if the contract is currently initializing. See {onlyInitializing}.
*/
function _isInitializing() internal view returns (bool) {
return _initializing;
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.9.0) (utils/Address.sol)
pragma solidity ^0.8.1;
/**
* @dev Collection of functions related to the address type
*/
library AddressUpgradeable {
/**
* @dev Returns true if `account` is a contract.
*
* [IMPORTANT]
* ====
* It is unsafe to assume that an address for which this function returns
* false is an externally-owned account (EOA) and not a contract.
*
* Among others, `isContract` will return false for the following
* types of addresses:
*
* - an externally-owned account
* - a contract in construction
* - an address where a contract will be created
* - an address where a contract lived, but was destroyed
*
* Furthermore, `isContract` will also return true if the target contract within
* the same transaction is already scheduled for destruction by `SELFDESTRUCT`,
* which only has an effect at the end of a transaction.
* ====
*
* [IMPORTANT]
* ====
* You shouldn't rely on `isContract` to protect against flash loan attacks!
*
* Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
* constructor.
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize/address.code.length, which returns 0
// for contracts in construction, since the code is only stored at the end
// of the constructor execution.
return account.code.length > 0;
}
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://consensys.net/diligence/blog/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.8.0/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason, it is bubbled up by this
* function (like regular Solidity function calls).
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*
* _Available since v3.1._
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*
* _Available since v3.1._
*/
function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
return functionDelegateCall(target, data, "Address: low-level delegate call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling
* the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract.
*
* _Available since v4.8._
*/
function verifyCallResultFromTarget(
address target,
bool success,
bytes memory returndata,
string memory errorMessage
) internal view returns (bytes memory) {
if (success) {
if (returndata.length == 0) {
// only check isContract if the call was successful and the return data is empty
// otherwise we already know that it was a contract
require(isContract(target), "Address: call to non-contract");
}
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
/**
* @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason or using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
function _revert(bytes memory returndata, string memory errorMessage) private pure {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
/// @solidity memory-safe-assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)
pragma solidity ^0.8.0;
import "../proxy/utils/Initializable.sol";
/**
* @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 ContextUpgradeable is Initializable {
function __Context_init() internal onlyInitializing {
}
function __Context_init_unchained() internal onlyInitializing {
}
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[50] private __gap;
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.9.0) (utils/Address.sol)
pragma solidity ^0.8.1;
/**
* @dev Collection of functions related to the address type
*/
library Address {
/**
* @dev Returns true if `account` is a contract.
*
* [IMPORTANT]
* ====
* It is unsafe to assume that an address for which this function returns
* false is an externally-owned account (EOA) and not a contract.
*
* Among others, `isContract` will return false for the following
* types of addresses:
*
* - an externally-owned account
* - a contract in construction
* - an address where a contract will be created
* - an address where a contract lived, but was destroyed
*
* Furthermore, `isContract` will also return true if the target contract within
* the same transaction is already scheduled for destruction by `SELFDESTRUCT`,
* which only has an effect at the end of a transaction.
* ====
*
* [IMPORTANT]
* ====
* You shouldn't rely on `isContract` to protect against flash loan attacks!
*
* Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
* constructor.
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize/address.code.length, which returns 0
// for contracts in construction, since the code is only stored at the end
// of the constructor execution.
return account.code.length > 0;
}
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://consensys.net/diligence/blog/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.8.0/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason, it is bubbled up by this
* function (like regular Solidity function calls).
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*
* _Available since v3.1._
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*
* _Available since v3.1._
*/
function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
return functionDelegateCall(target, data, "Address: low-level delegate call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling
* the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract.
*
* _Available since v4.8._
*/
function verifyCallResultFromTarget(
address target,
bool success,
bytes memory returndata,
string memory errorMessage
) internal view returns (bytes memory) {
if (success) {
if (returndata.length == 0) {
// only check isContract if the call was successful and the return data is empty
// otherwise we already know that it was a contract
require(isContract(target), "Address: call to non-contract");
}
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
/**
* @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason or using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
function _revert(bytes memory returndata, string memory errorMessage) private pure {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
/// @solidity memory-safe-assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.6.11;
/**
* @title PackageVersioned
* @notice Package version getter for contracts
**/
abstract contract PackageVersioned {
// GENERATED CODE - DO NOT EDIT
string public constant PACKAGE_VERSION = "7.1.10";
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.6.11;
interface IInterchainSecurityModule {
enum Types {
UNUSED,
ROUTING,
AGGREGATION,
LEGACY_MULTISIG,
MERKLE_ROOT_MULTISIG,
MESSAGE_ID_MULTISIG,
NULL, // used with relayer carrying no metadata
CCIP_READ,
ARB_L2_TO_L1,
WEIGHTED_MERKLE_ROOT_MULTISIG,
WEIGHTED_MESSAGE_ID_MULTISIG,
OP_L2_TO_L1
}
/**
* @notice Returns an enum that represents the type of security model
* encoded by this ISM.
* @dev Relayers infer how to fetch and format metadata.
*/
function moduleType() external view returns (uint8);
/**
* @notice Defines a security model responsible for verifying interchain
* messages based on the provided metadata.
* @param _metadata Off-chain metadata provided by a relayer, specific to
* the security model encoded by the module (e.g. validator signatures)
* @param _message Hyperlane encoded interchain message
* @return True if the message was verified
*/
function verify(
bytes calldata _metadata,
bytes calldata _message
) external returns (bool);
}
interface ISpecifiesInterchainSecurityModule {
function interchainSecurityModule()
external
view
returns (IInterchainSecurityModule);
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.8.0;
import {IInterchainSecurityModule} from "./IInterchainSecurityModule.sol";
import {IPostDispatchHook} from "./hooks/IPostDispatchHook.sol";
interface IMailbox {
// ============ Events ============
/**
* @notice Emitted when a new message is dispatched via Hyperlane
* @param sender The address that dispatched the message
* @param destination The destination domain of the message
* @param recipient The message recipient address on `destination`
* @param message Raw bytes of message
*/
event Dispatch(
address indexed sender,
uint32 indexed destination,
bytes32 indexed recipient,
bytes message
);
/**
* @notice Emitted when a new message is dispatched via Hyperlane
* @param messageId The unique message identifier
*/
event DispatchId(bytes32 indexed messageId);
/**
* @notice Emitted when a Hyperlane message is processed
* @param messageId The unique message identifier
*/
event ProcessId(bytes32 indexed messageId);
/**
* @notice Emitted when a Hyperlane message is delivered
* @param origin The origin domain of the message
* @param sender The message sender address on `origin`
* @param recipient The address that handled the message
*/
event Process(
uint32 indexed origin,
bytes32 indexed sender,
address indexed recipient
);
function localDomain() external view returns (uint32);
function delivered(bytes32 messageId) external view returns (bool);
function defaultIsm() external view returns (IInterchainSecurityModule);
function defaultHook() external view returns (IPostDispatchHook);
function requiredHook() external view returns (IPostDispatchHook);
function latestDispatchedId() external view returns (bytes32);
function dispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody
) external payable returns (bytes32 messageId);
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody
) external view returns (uint256 fee);
function dispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata body,
bytes calldata defaultHookMetadata
) external payable returns (bytes32 messageId);
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata defaultHookMetadata
) external view returns (uint256 fee);
function dispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata body,
bytes calldata customHookMetadata,
IPostDispatchHook customHook
) external payable returns (bytes32 messageId);
function quoteDispatch(
uint32 destinationDomain,
bytes32 recipientAddress,
bytes calldata messageBody,
bytes calldata customHookMetadata,
IPostDispatchHook customHook
) external view returns (uint256 fee);
function process(
bytes calldata metadata,
bytes calldata message
) external payable;
function recipientIsm(
address recipient
) external view returns (IInterchainSecurityModule module);
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.6.11;
interface IMessageRecipient {
function handle(
uint32 _origin,
bytes32 _sender,
bytes calldata _message
) external payable;
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.8.0;
/*@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@ HYPERLANE @@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@@
@@@@@@@@@ @@@@@@@@*/
interface IPostDispatchHook {
enum Types {
UNUSED,
ROUTING,
AGGREGATION,
MERKLE_TREE,
INTERCHAIN_GAS_PAYMASTER,
FALLBACK_ROUTING,
ID_AUTH_ISM,
PAUSABLE,
PROTOCOL_FEE,
LAYER_ZERO_V1,
RATE_LIMITED,
ARB_L2_TO_L1,
OP_L2_TO_L1,
MAILBOX_DEFAULT_HOOK,
AMOUNT_ROUTING
}
/**
* @notice Returns an enum that represents the type of hook
*/
function hookType() external view returns (uint8);
/**
* @notice Returns whether the hook supports metadata
* @param metadata metadata
* @return Whether the hook supports metadata
*/
function supportsMetadata(
bytes calldata metadata
) external view returns (bool);
/**
* @notice Post action after a message is dispatched via the Mailbox
* @param metadata The metadata required for the hook
* @param message The message passed from the Mailbox.dispatch() call
*/
function postDispatch(
bytes calldata metadata,
bytes calldata message
) external payable;
/**
* @notice Compute the payment required by the postDispatch call
* @param metadata The metadata required for the hook
* @param message The message passed from the Mailbox.dispatch() call
* @return Quoted payment for the postDispatch call
*/
function quoteDispatch(
bytes calldata metadata,
bytes calldata message
) external view returns (uint256);
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.8.0;
contract Indexed {
uint256 public immutable deployedBlock;
constructor() {
deployedBlock = block.number;
}
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.8.0;
import {TypeCasts} from "./TypeCasts.sol";
/**
* @title Hyperlane Message Library
* @notice Library for formatted messages used by Mailbox
**/
library Message {
using TypeCasts for bytes32;
uint256 private constant VERSION_OFFSET = 0;
uint256 private constant NONCE_OFFSET = 1;
uint256 private constant ORIGIN_OFFSET = 5;
uint256 private constant SENDER_OFFSET = 9;
uint256 private constant DESTINATION_OFFSET = 41;
uint256 private constant RECIPIENT_OFFSET = 45;
uint256 private constant BODY_OFFSET = 77;
/**
* @notice Returns formatted (packed) Hyperlane message with provided fields
* @dev This function should only be used in memory message construction.
* @param _version The version of the origin and destination Mailboxes
* @param _nonce A nonce to uniquely identify the message on its origin chain
* @param _originDomain Domain of origin chain
* @param _sender Address of sender as bytes32
* @param _destinationDomain Domain of destination chain
* @param _recipient Address of recipient on destination chain as bytes32
* @param _messageBody Raw bytes of message body
* @return Formatted message
*/
function formatMessage(
uint8 _version,
uint32 _nonce,
uint32 _originDomain,
bytes32 _sender,
uint32 _destinationDomain,
bytes32 _recipient,
bytes calldata _messageBody
) internal pure returns (bytes memory) {
return
abi.encodePacked(
_version,
_nonce,
_originDomain,
_sender,
_destinationDomain,
_recipient,
_messageBody
);
}
/**
* @notice Returns the message ID.
* @param _message ABI encoded Hyperlane message.
* @return ID of `_message`
*/
function id(bytes memory _message) internal pure returns (bytes32) {
return keccak256(_message);
}
/**
* @notice Returns the message version.
* @param _message ABI encoded Hyperlane message.
* @return Version of `_message`
*/
function version(bytes calldata _message) internal pure returns (uint8) {
return uint8(bytes1(_message[VERSION_OFFSET:NONCE_OFFSET]));
}
/**
* @notice Returns the message nonce.
* @param _message ABI encoded Hyperlane message.
* @return Nonce of `_message`
*/
function nonce(bytes calldata _message) internal pure returns (uint32) {
return uint32(bytes4(_message[NONCE_OFFSET:ORIGIN_OFFSET]));
}
/**
* @notice Returns the message origin domain.
* @param _message ABI encoded Hyperlane message.
* @return Origin domain of `_message`
*/
function origin(bytes calldata _message) internal pure returns (uint32) {
return uint32(bytes4(_message[ORIGIN_OFFSET:SENDER_OFFSET]));
}
/**
* @notice Returns the message sender as bytes32.
* @param _message ABI encoded Hyperlane message.
* @return Sender of `_message` as bytes32
*/
function sender(bytes calldata _message) internal pure returns (bytes32) {
return bytes32(_message[SENDER_OFFSET:DESTINATION_OFFSET]);
}
/**
* @notice Returns the message sender as address.
* @param _message ABI encoded Hyperlane message.
* @return Sender of `_message` as address
*/
function senderAddress(
bytes calldata _message
) internal pure returns (address) {
return sender(_message).bytes32ToAddress();
}
/**
* @notice Returns the message destination domain.
* @param _message ABI encoded Hyperlane message.
* @return Destination domain of `_message`
*/
function destination(
bytes calldata _message
) internal pure returns (uint32) {
return uint32(bytes4(_message[DESTINATION_OFFSET:RECIPIENT_OFFSET]));
}
/**
* @notice Returns the message recipient as bytes32.
* @param _message ABI encoded Hyperlane message.
* @return Recipient of `_message` as bytes32
*/
function recipient(
bytes calldata _message
) internal pure returns (bytes32) {
return bytes32(_message[RECIPIENT_OFFSET:BODY_OFFSET]);
}
/**
* @notice Returns the message recipient as address.
* @param _message ABI encoded Hyperlane message.
* @return Recipient of `_message` as address
*/
function recipientAddress(
bytes calldata _message
) internal pure returns (address) {
return recipient(_message).bytes32ToAddress();
}
/**
* @notice Returns the message body.
* @param _message ABI encoded Hyperlane message.
* @return Body of `_message`
*/
function body(
bytes calldata _message
) internal pure returns (bytes calldata) {
return bytes(_message[BODY_OFFSET:]);
}
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.6.11;
library TypeCasts {
// alignment preserving cast
function addressToBytes32(address _addr) internal pure returns (bytes32) {
return bytes32(uint256(uint160(_addr)));
}
// alignment preserving cast
function bytes32ToAddress(bytes32 _buf) internal pure returns (address) {
require(
uint256(_buf) <= uint256(type(uint160).max),
"TypeCasts: bytes32ToAddress overflow"
);
return address(uint160(uint256(_buf)));
}
}// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.6.11;
/**
* @title Versioned
* @notice Version getter for contracts
**/
contract Versioned {
uint8 public constant VERSION = 3;
}{
"evmVersion": "paris",
"libraries": {},
"optimizer": {
"enabled": true,
"runs": 999999
},
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"uint32","name":"_localDomain","type":"uint32"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"hook","type":"address"}],"name":"DefaultHookSet","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"module","type":"address"}],"name":"DefaultIsmSet","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"sender","type":"address"},{"indexed":true,"internalType":"uint32","name":"destination","type":"uint32"},{"indexed":true,"internalType":"bytes32","name":"recipient","type":"bytes32"},{"indexed":false,"internalType":"bytes","name":"message","type":"bytes"}],"name":"Dispatch","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"messageId","type":"bytes32"}],"name":"DispatchId","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint8","name":"version","type":"uint8"}],"name":"Initialized","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":true,"internalType":"uint32","name":"origin","type":"uint32"},{"indexed":true,"internalType":"bytes32","name":"sender","type":"bytes32"},{"indexed":true,"internalType":"address","name":"recipient","type":"address"}],"name":"Process","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"messageId","type":"bytes32"}],"name":"ProcessId","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"hook","type":"address"}],"name":"RequiredHookSet","type":"event"},{"inputs":[],"name":"PACKAGE_VERSION","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"VERSION","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"defaultHook","outputs":[{"internalType":"contract IPostDispatchHook","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"defaultIsm","outputs":[{"internalType":"contract IInterchainSecurityModule","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"_id","type":"bytes32"}],"name":"delivered","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"deployedBlock","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint32","name":"destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"messageBody","type":"bytes"},{"internalType":"bytes","name":"metadata","type":"bytes"},{"internalType":"contract IPostDispatchHook","name":"hook","type":"address"}],"name":"dispatch","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint32","name":"destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"messageBody","type":"bytes"},{"internalType":"bytes","name":"hookMetadata","type":"bytes"}],"name":"dispatch","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint32","name":"_destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"_recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"_messageBody","type":"bytes"}],"name":"dispatch","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"_owner","type":"address"},{"internalType":"address","name":"_defaultIsm","type":"address"},{"internalType":"address","name":"_defaultHook","type":"address"},{"internalType":"address","name":"_requiredHook","type":"address"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"latestDispatchedId","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"localDomain","outputs":[{"internalType":"uint32","name":"","type":"uint32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"nonce","outputs":[{"internalType":"uint32","name":"","type":"uint32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"_metadata","type":"bytes"},{"internalType":"bytes","name":"_message","type":"bytes"}],"name":"process","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"_id","type":"bytes32"}],"name":"processedAt","outputs":[{"internalType":"uint48","name":"","type":"uint48"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"_id","type":"bytes32"}],"name":"processor","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint32","name":"destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"messageBody","type":"bytes"},{"internalType":"bytes","name":"metadata","type":"bytes"},{"internalType":"contract IPostDispatchHook","name":"hook","type":"address"}],"name":"quoteDispatch","outputs":[{"internalType":"uint256","name":"fee","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint32","name":"destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"messageBody","type":"bytes"}],"name":"quoteDispatch","outputs":[{"internalType":"uint256","name":"fee","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint32","name":"destinationDomain","type":"uint32"},{"internalType":"bytes32","name":"recipientAddress","type":"bytes32"},{"internalType":"bytes","name":"messageBody","type":"bytes"},{"internalType":"bytes","name":"defaultHookMetadata","type":"bytes"}],"name":"quoteDispatch","outputs":[{"internalType":"uint256","name":"fee","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_recipient","type":"address"}],"name":"recipientIsm","outputs":[{"internalType":"contract IInterchainSecurityModule","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"requiredHook","outputs":[{"internalType":"contract IPostDispatchHook","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_hook","type":"address"}],"name":"setDefaultHook","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_module","type":"address"}],"name":"setDefaultIsm","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_hook","type":"address"}],"name":"setRequiredHook","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"}]Contract Creation Code
60c060405234801561001057600080fd5b50604051620022f3380380620022f383398101604081905261003191610043565b4360805263ffffffff1660a052610070565b60006020828403121561005557600080fd5b815163ffffffff8116811461006957600080fd5b9392505050565b60805160a05161224f620000a4600039600081816103d601528181610b0f0152611761015260006103a2015261224f6000f3fe6080604052600436106101ac5760003560e01c80638da5cb5b116100ec578063e70f48ac1161008a578063f7ccd32111610064578063f7ccd321146105d7578063f8c8765e146105f7578063fa31de0114610617578063ffa1ad741461062a57600080fd5b8063e70f48ac14610577578063f2fde38b14610597578063f794687a146105b757600080fd5b80639c42bd18116100c65780639c42bd18146104ae578063affed0e0146104ce578063d6d08a09146104eb578063e495f1d41461051857600080fd5b80638da5cb5b1461040d57806393c448471461043857806399b048091461048e57600080fd5b80635d1fe5a9116101595780637c39d130116101335780637c39d1301461035d57806381d2ea951461037057806382ea7bfe146103905780638d3638f4146103c457600080fd5b80635d1fe5a9146102d85780636e5f516e1461031b578063715018a61461034857600080fd5b80631426b7f41161018a5780631426b7f4146102515780633d1250b71461027357806348aee8d4146102c557600080fd5b806307a2fda1146101b157806310b83dc01461021a578063134fbb4f1461023b575b600080fd5b3480156101bd57600080fd5b506101fe6101cc366004611b6a565b6000908152606a602052604090205474010000000000000000000000000000000000000000900465ffffffffffff1690565b60405165ffffffffffff90911681526020015b60405180910390f35b61022d610228366004611c00565b610651565b604051908152602001610211565b34801561024757600080fd5b5061022d60665481565b34801561025d57600080fd5b5061027161026c366004611c9e565b610925565b005b34801561027f57600080fd5b506068546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b60405173ffffffffffffffffffffffffffffffffffffffff9091168152602001610211565b61022d6102d3366004611cbb565b610a45565b3480156102e457600080fd5b506102a06102f3366004611b6a565b6000908152606a602052604090205473ffffffffffffffffffffffffffffffffffffffff1690565b34801561032757600080fd5b506067546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b34801561035457600080fd5b50610271610a83565b61027161036b366004611d45565b610a97565b34801561037c57600080fd5b5061022d61038b366004611c00565b610f39565b34801561039c57600080fd5b5061022d7f000000000000000000000000000000000000000000000000000000000000000081565b3480156103d057600080fd5b506103f87f000000000000000000000000000000000000000000000000000000000000000081565b60405163ffffffff9091168152602001610211565b34801561041957600080fd5b5060335473ffffffffffffffffffffffffffffffffffffffff166102a0565b34801561044457600080fd5b506104816040518060400160405280600681526020017f372e312e3130000000000000000000000000000000000000000000000000000081525081565b6040516102119190611e1f565b34801561049a57600080fd5b506102716104a9366004611c9e565b6110cc565b3480156104ba57600080fd5b5061022d6104c9366004611e32565b6111e7565b3480156104da57600080fd5b506065546103f89063ffffffff1681565b3480156104f757600080fd5b506069546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b34801561052457600080fd5b50610567610533366004611b6a565b6000908152606a602052604090205474010000000000000000000000000000000000000000900465ffffffffffff16151590565b6040519015158152602001610211565b34801561058357600080fd5b506102a0610592366004611c9e565b611223565b3480156105a357600080fd5b506102716105b2366004611c9e565b61135a565b3480156105c357600080fd5b506102716105d2366004611c9e565b611411565b3480156105e357600080fd5b5061022d6105f2366004611cbb565b61152c565b34801561060357600080fd5b50610271610612366004611e80565b61155f565b61022d610625366004611e32565b611719565b34801561063657600080fd5b5061063f600381565b60405160ff9091168152602001610211565b600073ffffffffffffffffffffffffffffffffffffffff821661068a5760685473ffffffffffffffffffffffffffffffffffffffff1691505b60006106988989898961174c565b805160208201206066819055606580549293509091600191906000906106c590849063ffffffff16611f0b565b92506101000a81548163ffffffff021916908363ffffffff160217905550888a63ffffffff163373ffffffffffffffffffffffffffffffffffffffff167f769f711d20c679153d382254f59892613b58a97cc876b249134ac25c80f9c814856040516107319190611e1f565b60405180910390a460405181907f788dbc1b7152732178210e7f4d9d010ef016f9eafbe66786bd7169f56e0c353a90600090a26069546040517faaccd23000000000000000000000000000000000000000000000000000000000815260009173ffffffffffffffffffffffffffffffffffffffff169063aaccd230906107bf908a908a908890600401611f78565b602060405180830381865afa1580156107dc573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108009190611fa8565b90508034101561080d5750345b6069546040517f086011b900000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff9091169063086011b9908390610869908b908b908990600401611f78565b6000604051808303818588803b15801561088257600080fd5b505af1158015610896573d6000803e3d6000fd5b50505050508473ffffffffffffffffffffffffffffffffffffffff1663086011b982346108c39190611fc1565b8989876040518563ffffffff1660e01b81526004016108e493929190611f78565b6000604051808303818588803b1580156108fd57600080fd5b505af1158015610911573d6000803e3d6000fd5b50949e9d5050505050505050505050505050565b61092d611795565b73ffffffffffffffffffffffffffffffffffffffff81163b6109d6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602360248201527f4d61696c626f783a20726571756972656420686f6f6b206e6f7420636f6e747260448201527f616374000000000000000000000000000000000000000000000000000000000060648201526084015b60405180910390fd5b606980547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517f329ec8e2438a73828ecf31a6568d7a91d7b1d79e342b0692914fd053d1a002b190600090a250565b6000610a78878787878787606860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16610651565b979650505050505050565b610a8b611795565b610a956000611816565b565b6003610aa3838361188d565b60ff1614610b0d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601460248201527f4d61696c626f783a206261642076657273696f6e00000000000000000000000060448201526064016109cd565b7f000000000000000000000000000000000000000000000000000000000000000063ffffffff16610b3e83836118b1565b63ffffffff1614610bab576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601f60248201527f4d61696c626f783a20756e65787065637465642064657374696e6174696f6e0060448201526064016109cd565b6000610bec83838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061178a92505050565b6000818152606a602052604090205490915074010000000000000000000000000000000000000000900465ffffffffffff1615610c85576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601a60248201527f4d61696c626f783a20616c72656164792064656c69766572656400000000000060448201526064016109cd565b6000610c9184846118d4565b90506000610c9e82611223565b60408051808201825233815265ffffffffffff43811660208084019182526000898152606a9091529390932091518254935190911674010000000000000000000000000000000000000000027fffffffffffff000000000000000000000000000000000000000000000000000090931673ffffffffffffffffffffffffffffffffffffffff918216179290921790559091508216610d3c86866118ef565b610d468787611908565b63ffffffff167f0d381c2a574ae8f04e213db7cfb4df8df712cdbd427d9868ffef380660ca657460405160405180910390a460405183907f1cae38cdd3d3919489272725a5ae62a4f48b2989b0dae843d3c279fee18073a990600090a26040517ff7e83aee00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82169063f7e83aee90610dfb908a908a908a908a90600401611fd4565b6020604051808303816000875af1158015610e1a573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610e3e9190611ffb565b610ea4576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820181905260248201527f4d61696c626f783a2049534d20766572696669636174696f6e206661696c656460448201526064016109cd565b8173ffffffffffffffffffffffffffffffffffffffff166356d5d47534610ecb8888611908565b610ed589896118ef565b610edf8a8a611918565b6040518663ffffffff1660e01b8152600401610efe949392919061201d565b6000604051808303818588803b158015610f1757600080fd5b505af1158015610f2b573d6000803e3d6000fd5b505050505050505050505050565b600073ffffffffffffffffffffffffffffffffffffffff8216610f725760685473ffffffffffffffffffffffffffffffffffffffff1691505b6000610f808989898961174c565b6040517faaccd23000000000000000000000000000000000000000000000000000000000815290915073ffffffffffffffffffffffffffffffffffffffff84169063aaccd23090610fd990889088908690600401611f78565b602060405180830381865afa158015610ff6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061101a9190611fa8565b6069546040517faaccd23000000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff9091169063aaccd2309061107490899089908790600401611f78565b602060405180830381865afa158015611091573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110b59190611fa8565b6110bf9190612043565b9998505050505050505050565b6110d4611795565b73ffffffffffffffffffffffffffffffffffffffff81163b611178576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602260248201527f4d61696c626f783a2064656661756c7420686f6f6b206e6f7420636f6e74726160448201527f637400000000000000000000000000000000000000000000000000000000000060648201526084016109cd565b606880547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517f65a63e5066ee2fcdf9d32a7f1bf7ce71c76066f19d0609dddccd334ab87237d790600090a250565b600061121a858585856111fc86808385612056565b60685473ffffffffffffffffffffffffffffffffffffffff16610f39565b95945050505050565b60408051600481526024810182526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fde523cf30000000000000000000000000000000000000000000000000000000017905290516000918291829173ffffffffffffffffffffffffffffffffffffffff8616916112a49190612080565b600060405180830381855afa9150503d80600081146112df576040519150601f19603f3d011682016040523d82523d6000602084013e6112e4565b606091505b50915091508180156112f65750805115155b1561133957600081806020019051810190611311919061209c565b905073ffffffffffffffffffffffffffffffffffffffff81161561133757949350505050565b505b505060675473ffffffffffffffffffffffffffffffffffffffff1692915050565b611362611795565b73ffffffffffffffffffffffffffffffffffffffff8116611405576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201527f646472657373000000000000000000000000000000000000000000000000000060648201526084016109cd565b61140e81611816565b50565b611419611795565b73ffffffffffffffffffffffffffffffffffffffff81163b6114bd576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602160248201527f4d61696c626f783a2064656661756c742049534d206e6f7420636f6e7472616360448201527f740000000000000000000000000000000000000000000000000000000000000060648201526084016109cd565b606780547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517fa76ad0adbf45318f8633aa0210f711273d50fbb6fef76ed95bbae97082c75daa90600090a250565b6000610a78878787878787606860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16610f39565b600054610100900460ff161580801561157f5750600054600160ff909116105b806115995750303b158015611599575060005460ff166001145b611625576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602e60248201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160448201527f647920696e697469616c697a656400000000000000000000000000000000000060648201526084016109cd565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055801561168357600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff166101001790555b61168b611934565b61169484611411565b61169d836110cc565b6116a682610925565b6116af8561135a565b801561171257600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff169055604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb38474024989060200160405180910390a15b5050505050565b600061121a8585858561172e86808385612056565b60685473ffffffffffffffffffffffffffffffffffffffff16610651565b60655460609061121a9060039063ffffffff167f000000000000000000000000000000000000000000000000000000000000000033898989896119d3565b805160209091012090565b60335473ffffffffffffffffffffffffffffffffffffffff163314610a95576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016109cd565b6033805473ffffffffffffffffffffffffffffffffffffffff8381167fffffffffffffffffffffffff0000000000000000000000000000000000000000831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b600061189c6001828486612056565b6118a5916120b9565b60f81c90505b92915050565b60006118c1602d60298486612056565b6118ca91612101565b60e01c9392505050565b60006118e86118e38484611a11565b611a21565b9392505050565b60006118ff602960098486612056565b6118e891612147565b60006118c1600960058486612056565b36600061192883604d8187612056565b915091505b9250929050565b600054610100900460ff166119cb576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201527f6e697469616c697a696e6700000000000000000000000000000000000000000060648201526084016109cd565b610a95611aca565b606088888888888888886040516020016119f4989796959493929190612183565b604051602081830303815290604052905098975050505050505050565b60006118ff604d602d8486612056565b600073ffffffffffffffffffffffffffffffffffffffff821115611ac6576040517f08c379a0000000000000000000000000000000000000000000000000000000008152602060048201526024808201527f5479706543617374733a2062797465733332546f41646472657373206f76657260448201527f666c6f770000000000000000000000000000000000000000000000000000000060648201526084016109cd565b5090565b600054610100900460ff16611b61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201527f6e697469616c697a696e6700000000000000000000000000000000000000000060648201526084016109cd565b610a9533611816565b600060208284031215611b7c57600080fd5b5035919050565b803563ffffffff81168114611b9757600080fd5b919050565b60008083601f840112611bae57600080fd5b50813567ffffffffffffffff811115611bc657600080fd5b60208301915083602082850101111561192d57600080fd5b73ffffffffffffffffffffffffffffffffffffffff8116811461140e57600080fd5b600080600080600080600060a0888a031215611c1b57600080fd5b611c2488611b83565b965060208801359550604088013567ffffffffffffffff80821115611c4857600080fd5b611c548b838c01611b9c565b909750955060608a0135915080821115611c6d57600080fd5b50611c7a8a828b01611b9c565b9094509250506080880135611c8e81611bde565b8091505092959891949750929550565b600060208284031215611cb057600080fd5b81356118e881611bde565b60008060008060008060808789031215611cd457600080fd5b611cdd87611b83565b955060208701359450604087013567ffffffffffffffff80821115611d0157600080fd5b611d0d8a838b01611b9c565b90965094506060890135915080821115611d2657600080fd5b50611d3389828a01611b9c565b979a9699509497509295939492505050565b60008060008060408587031215611d5b57600080fd5b843567ffffffffffffffff80821115611d7357600080fd5b611d7f88838901611b9c565b90965094506020870135915080821115611d9857600080fd5b50611da587828801611b9c565b95989497509550505050565b60005b83811015611dcc578181015183820152602001611db4565b50506000910152565b60008151808452611ded816020860160208601611db1565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b6020815260006118e86020830184611dd5565b60008060008060608587031215611e4857600080fd5b611e5185611b83565b935060208501359250604085013567ffffffffffffffff811115611e7457600080fd5b611da587828801611b9c565b60008060008060808587031215611e9657600080fd5b8435611ea181611bde565b93506020850135611eb181611bde565b92506040850135611ec181611bde565b91506060850135611ed181611bde565b939692955090935050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b63ffffffff818116838216019080821115611f2857611f28611edc565b5092915050565b8183528181602085013750600060208284010152600060207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0601f840116840101905092915050565b604081526000611f8c604083018587611f2f565b8281036020840152611f9e8185611dd5565b9695505050505050565b600060208284031215611fba57600080fd5b5051919050565b818103818111156118ab576118ab611edc565b604081526000611fe8604083018688611f2f565b8281036020840152610a78818587611f2f565b60006020828403121561200d57600080fd5b815180151581146118e857600080fd5b63ffffffff85168152836020820152606060408201526000611f9e606083018486611f2f565b808201808211156118ab576118ab611edc565b6000808585111561206657600080fd5b8386111561207357600080fd5b5050820193919092039150565b60008251612092818460208701611db1565b9190910192915050565b6000602082840312156120ae57600080fd5b81516118e881611bde565b7fff0000000000000000000000000000000000000000000000000000000000000081358181169160018510156120f95780818660010360031b1b83161692505b505092915050565b7fffffffff0000000000000000000000000000000000000000000000000000000081358181169160048510156120f95760049490940360031b84901b1690921692915050565b803560208310156118ab577fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff602084900360031b1b1692915050565b7fff000000000000000000000000000000000000000000000000000000000000008960f81b16815260007fffffffff00000000000000000000000000000000000000000000000000000000808a60e01b166001840152808960e01b166005840152876009840152808760e01b1660298401525084602d8301528284604d8401375060009101604d0190815297965050505050505056fea2646970667358221220d773402ca89d035dabb4a42f8da6f28bf6d3aebd4dfda652108bee8bde8d81cd64736f6c6343000816003300000000000000000000000000000000000000000000000000000000000b67d2
Deployed Bytecode
0x6080604052600436106101ac5760003560e01c80638da5cb5b116100ec578063e70f48ac1161008a578063f7ccd32111610064578063f7ccd321146105d7578063f8c8765e146105f7578063fa31de0114610617578063ffa1ad741461062a57600080fd5b8063e70f48ac14610577578063f2fde38b14610597578063f794687a146105b757600080fd5b80639c42bd18116100c65780639c42bd18146104ae578063affed0e0146104ce578063d6d08a09146104eb578063e495f1d41461051857600080fd5b80638da5cb5b1461040d57806393c448471461043857806399b048091461048e57600080fd5b80635d1fe5a9116101595780637c39d130116101335780637c39d1301461035d57806381d2ea951461037057806382ea7bfe146103905780638d3638f4146103c457600080fd5b80635d1fe5a9146102d85780636e5f516e1461031b578063715018a61461034857600080fd5b80631426b7f41161018a5780631426b7f4146102515780633d1250b71461027357806348aee8d4146102c557600080fd5b806307a2fda1146101b157806310b83dc01461021a578063134fbb4f1461023b575b600080fd5b3480156101bd57600080fd5b506101fe6101cc366004611b6a565b6000908152606a602052604090205474010000000000000000000000000000000000000000900465ffffffffffff1690565b60405165ffffffffffff90911681526020015b60405180910390f35b61022d610228366004611c00565b610651565b604051908152602001610211565b34801561024757600080fd5b5061022d60665481565b34801561025d57600080fd5b5061027161026c366004611c9e565b610925565b005b34801561027f57600080fd5b506068546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b60405173ffffffffffffffffffffffffffffffffffffffff9091168152602001610211565b61022d6102d3366004611cbb565b610a45565b3480156102e457600080fd5b506102a06102f3366004611b6a565b6000908152606a602052604090205473ffffffffffffffffffffffffffffffffffffffff1690565b34801561032757600080fd5b506067546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b34801561035457600080fd5b50610271610a83565b61027161036b366004611d45565b610a97565b34801561037c57600080fd5b5061022d61038b366004611c00565b610f39565b34801561039c57600080fd5b5061022d7f000000000000000000000000000000000000000000000000000000000022ef2381565b3480156103d057600080fd5b506103f87f00000000000000000000000000000000000000000000000000000000000b67d281565b60405163ffffffff9091168152602001610211565b34801561041957600080fd5b5060335473ffffffffffffffffffffffffffffffffffffffff166102a0565b34801561044457600080fd5b506104816040518060400160405280600681526020017f372e312e3130000000000000000000000000000000000000000000000000000081525081565b6040516102119190611e1f565b34801561049a57600080fd5b506102716104a9366004611c9e565b6110cc565b3480156104ba57600080fd5b5061022d6104c9366004611e32565b6111e7565b3480156104da57600080fd5b506065546103f89063ffffffff1681565b3480156104f757600080fd5b506069546102a09073ffffffffffffffffffffffffffffffffffffffff1681565b34801561052457600080fd5b50610567610533366004611b6a565b6000908152606a602052604090205474010000000000000000000000000000000000000000900465ffffffffffff16151590565b6040519015158152602001610211565b34801561058357600080fd5b506102a0610592366004611c9e565b611223565b3480156105a357600080fd5b506102716105b2366004611c9e565b61135a565b3480156105c357600080fd5b506102716105d2366004611c9e565b611411565b3480156105e357600080fd5b5061022d6105f2366004611cbb565b61152c565b34801561060357600080fd5b50610271610612366004611e80565b61155f565b61022d610625366004611e32565b611719565b34801561063657600080fd5b5061063f600381565b60405160ff9091168152602001610211565b600073ffffffffffffffffffffffffffffffffffffffff821661068a5760685473ffffffffffffffffffffffffffffffffffffffff1691505b60006106988989898961174c565b805160208201206066819055606580549293509091600191906000906106c590849063ffffffff16611f0b565b92506101000a81548163ffffffff021916908363ffffffff160217905550888a63ffffffff163373ffffffffffffffffffffffffffffffffffffffff167f769f711d20c679153d382254f59892613b58a97cc876b249134ac25c80f9c814856040516107319190611e1f565b60405180910390a460405181907f788dbc1b7152732178210e7f4d9d010ef016f9eafbe66786bd7169f56e0c353a90600090a26069546040517faaccd23000000000000000000000000000000000000000000000000000000000815260009173ffffffffffffffffffffffffffffffffffffffff169063aaccd230906107bf908a908a908890600401611f78565b602060405180830381865afa1580156107dc573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108009190611fa8565b90508034101561080d5750345b6069546040517f086011b900000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff9091169063086011b9908390610869908b908b908990600401611f78565b6000604051808303818588803b15801561088257600080fd5b505af1158015610896573d6000803e3d6000fd5b50505050508473ffffffffffffffffffffffffffffffffffffffff1663086011b982346108c39190611fc1565b8989876040518563ffffffff1660e01b81526004016108e493929190611f78565b6000604051808303818588803b1580156108fd57600080fd5b505af1158015610911573d6000803e3d6000fd5b50949e9d5050505050505050505050505050565b61092d611795565b73ffffffffffffffffffffffffffffffffffffffff81163b6109d6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602360248201527f4d61696c626f783a20726571756972656420686f6f6b206e6f7420636f6e747260448201527f616374000000000000000000000000000000000000000000000000000000000060648201526084015b60405180910390fd5b606980547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517f329ec8e2438a73828ecf31a6568d7a91d7b1d79e342b0692914fd053d1a002b190600090a250565b6000610a78878787878787606860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16610651565b979650505050505050565b610a8b611795565b610a956000611816565b565b6003610aa3838361188d565b60ff1614610b0d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601460248201527f4d61696c626f783a206261642076657273696f6e00000000000000000000000060448201526064016109cd565b7f00000000000000000000000000000000000000000000000000000000000b67d263ffffffff16610b3e83836118b1565b63ffffffff1614610bab576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601f60248201527f4d61696c626f783a20756e65787065637465642064657374696e6174696f6e0060448201526064016109cd565b6000610bec83838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061178a92505050565b6000818152606a602052604090205490915074010000000000000000000000000000000000000000900465ffffffffffff1615610c85576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601a60248201527f4d61696c626f783a20616c72656164792064656c69766572656400000000000060448201526064016109cd565b6000610c9184846118d4565b90506000610c9e82611223565b60408051808201825233815265ffffffffffff43811660208084019182526000898152606a9091529390932091518254935190911674010000000000000000000000000000000000000000027fffffffffffff000000000000000000000000000000000000000000000000000090931673ffffffffffffffffffffffffffffffffffffffff918216179290921790559091508216610d3c86866118ef565b610d468787611908565b63ffffffff167f0d381c2a574ae8f04e213db7cfb4df8df712cdbd427d9868ffef380660ca657460405160405180910390a460405183907f1cae38cdd3d3919489272725a5ae62a4f48b2989b0dae843d3c279fee18073a990600090a26040517ff7e83aee00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82169063f7e83aee90610dfb908a908a908a908a90600401611fd4565b6020604051808303816000875af1158015610e1a573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610e3e9190611ffb565b610ea4576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820181905260248201527f4d61696c626f783a2049534d20766572696669636174696f6e206661696c656460448201526064016109cd565b8173ffffffffffffffffffffffffffffffffffffffff166356d5d47534610ecb8888611908565b610ed589896118ef565b610edf8a8a611918565b6040518663ffffffff1660e01b8152600401610efe949392919061201d565b6000604051808303818588803b158015610f1757600080fd5b505af1158015610f2b573d6000803e3d6000fd5b505050505050505050505050565b600073ffffffffffffffffffffffffffffffffffffffff8216610f725760685473ffffffffffffffffffffffffffffffffffffffff1691505b6000610f808989898961174c565b6040517faaccd23000000000000000000000000000000000000000000000000000000000815290915073ffffffffffffffffffffffffffffffffffffffff84169063aaccd23090610fd990889088908690600401611f78565b602060405180830381865afa158015610ff6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061101a9190611fa8565b6069546040517faaccd23000000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff9091169063aaccd2309061107490899089908790600401611f78565b602060405180830381865afa158015611091573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110b59190611fa8565b6110bf9190612043565b9998505050505050505050565b6110d4611795565b73ffffffffffffffffffffffffffffffffffffffff81163b611178576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602260248201527f4d61696c626f783a2064656661756c7420686f6f6b206e6f7420636f6e74726160448201527f637400000000000000000000000000000000000000000000000000000000000060648201526084016109cd565b606880547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517f65a63e5066ee2fcdf9d32a7f1bf7ce71c76066f19d0609dddccd334ab87237d790600090a250565b600061121a858585856111fc86808385612056565b60685473ffffffffffffffffffffffffffffffffffffffff16610f39565b95945050505050565b60408051600481526024810182526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fde523cf30000000000000000000000000000000000000000000000000000000017905290516000918291829173ffffffffffffffffffffffffffffffffffffffff8616916112a49190612080565b600060405180830381855afa9150503d80600081146112df576040519150601f19603f3d011682016040523d82523d6000602084013e6112e4565b606091505b50915091508180156112f65750805115155b1561133957600081806020019051810190611311919061209c565b905073ffffffffffffffffffffffffffffffffffffffff81161561133757949350505050565b505b505060675473ffffffffffffffffffffffffffffffffffffffff1692915050565b611362611795565b73ffffffffffffffffffffffffffffffffffffffff8116611405576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201527f646472657373000000000000000000000000000000000000000000000000000060648201526084016109cd565b61140e81611816565b50565b611419611795565b73ffffffffffffffffffffffffffffffffffffffff81163b6114bd576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602160248201527f4d61696c626f783a2064656661756c742049534d206e6f7420636f6e7472616360448201527f740000000000000000000000000000000000000000000000000000000000000060648201526084016109cd565b606780547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff83169081179091556040517fa76ad0adbf45318f8633aa0210f711273d50fbb6fef76ed95bbae97082c75daa90600090a250565b6000610a78878787878787606860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16610f39565b600054610100900460ff161580801561157f5750600054600160ff909116105b806115995750303b158015611599575060005460ff166001145b611625576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602e60248201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160448201527f647920696e697469616c697a656400000000000000000000000000000000000060648201526084016109cd565b600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055801561168357600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff166101001790555b61168b611934565b61169484611411565b61169d836110cc565b6116a682610925565b6116af8561135a565b801561171257600080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff169055604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb38474024989060200160405180910390a15b5050505050565b600061121a8585858561172e86808385612056565b60685473ffffffffffffffffffffffffffffffffffffffff16610651565b60655460609061121a9060039063ffffffff167f00000000000000000000000000000000000000000000000000000000000b67d233898989896119d3565b805160209091012090565b60335473ffffffffffffffffffffffffffffffffffffffff163314610a95576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064016109cd565b6033805473ffffffffffffffffffffffffffffffffffffffff8381167fffffffffffffffffffffffff0000000000000000000000000000000000000000831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b600061189c6001828486612056565b6118a5916120b9565b60f81c90505b92915050565b60006118c1602d60298486612056565b6118ca91612101565b60e01c9392505050565b60006118e86118e38484611a11565b611a21565b9392505050565b60006118ff602960098486612056565b6118e891612147565b60006118c1600960058486612056565b36600061192883604d8187612056565b915091505b9250929050565b600054610100900460ff166119cb576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201527f6e697469616c697a696e6700000000000000000000000000000000000000000060648201526084016109cd565b610a95611aca565b606088888888888888886040516020016119f4989796959493929190612183565b604051602081830303815290604052905098975050505050505050565b60006118ff604d602d8486612056565b600073ffffffffffffffffffffffffffffffffffffffff821115611ac6576040517f08c379a0000000000000000000000000000000000000000000000000000000008152602060048201526024808201527f5479706543617374733a2062797465733332546f41646472657373206f76657260448201527f666c6f770000000000000000000000000000000000000000000000000000000060648201526084016109cd565b5090565b600054610100900460ff16611b61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201527f6e697469616c697a696e6700000000000000000000000000000000000000000060648201526084016109cd565b610a9533611816565b600060208284031215611b7c57600080fd5b5035919050565b803563ffffffff81168114611b9757600080fd5b919050565b60008083601f840112611bae57600080fd5b50813567ffffffffffffffff811115611bc657600080fd5b60208301915083602082850101111561192d57600080fd5b73ffffffffffffffffffffffffffffffffffffffff8116811461140e57600080fd5b600080600080600080600060a0888a031215611c1b57600080fd5b611c2488611b83565b965060208801359550604088013567ffffffffffffffff80821115611c4857600080fd5b611c548b838c01611b9c565b909750955060608a0135915080821115611c6d57600080fd5b50611c7a8a828b01611b9c565b9094509250506080880135611c8e81611bde565b8091505092959891949750929550565b600060208284031215611cb057600080fd5b81356118e881611bde565b60008060008060008060808789031215611cd457600080fd5b611cdd87611b83565b955060208701359450604087013567ffffffffffffffff80821115611d0157600080fd5b611d0d8a838b01611b9c565b90965094506060890135915080821115611d2657600080fd5b50611d3389828a01611b9c565b979a9699509497509295939492505050565b60008060008060408587031215611d5b57600080fd5b843567ffffffffffffffff80821115611d7357600080fd5b611d7f88838901611b9c565b90965094506020870135915080821115611d9857600080fd5b50611da587828801611b9c565b95989497509550505050565b60005b83811015611dcc578181015183820152602001611db4565b50506000910152565b60008151808452611ded816020860160208601611db1565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b6020815260006118e86020830184611dd5565b60008060008060608587031215611e4857600080fd5b611e5185611b83565b935060208501359250604085013567ffffffffffffffff811115611e7457600080fd5b611da587828801611b9c565b60008060008060808587031215611e9657600080fd5b8435611ea181611bde565b93506020850135611eb181611bde565b92506040850135611ec181611bde565b91506060850135611ed181611bde565b939692955090935050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b63ffffffff818116838216019080821115611f2857611f28611edc565b5092915050565b8183528181602085013750600060208284010152600060207fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0601f840116840101905092915050565b604081526000611f8c604083018587611f2f565b8281036020840152611f9e8185611dd5565b9695505050505050565b600060208284031215611fba57600080fd5b5051919050565b818103818111156118ab576118ab611edc565b604081526000611fe8604083018688611f2f565b8281036020840152610a78818587611f2f565b60006020828403121561200d57600080fd5b815180151581146118e857600080fd5b63ffffffff85168152836020820152606060408201526000611f9e606083018486611f2f565b808201808211156118ab576118ab611edc565b6000808585111561206657600080fd5b8386111561207357600080fd5b5050820193919092039150565b60008251612092818460208701611db1565b9190910192915050565b6000602082840312156120ae57600080fd5b81516118e881611bde565b7fff0000000000000000000000000000000000000000000000000000000000000081358181169160018510156120f95780818660010360031b1b83161692505b505092915050565b7fffffffff0000000000000000000000000000000000000000000000000000000081358181169160048510156120f95760049490940360031b84901b1690921692915050565b803560208310156118ab577fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff602084900360031b1b1692915050565b7fff000000000000000000000000000000000000000000000000000000000000008960f81b16815260007fffffffff00000000000000000000000000000000000000000000000000000000808a60e01b166001840152808960e01b166005840152876009840152808760e01b1660298401525084602d8301528284604d8401375060009101604d0190815297965050505050505056fea2646970667358221220d773402ca89d035dabb4a42f8da6f28bf6d3aebd4dfda652108bee8bde8d81cd64736f6c63430008160033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
00000000000000000000000000000000000000000000000000000000000b67d2
-----Decoded View---------------
Arg [0] : _localDomain (uint32): 747474
-----Encoded View---------------
1 Constructor Arguments found :
Arg [0] : 00000000000000000000000000000000000000000000000000000000000b67d2
Loading...
Loading
Loading...
Loading
Loading...
Loading
Loading...
Loading
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.