ETH Price: $2,377.93 (-10.56%)

Contract

0x69009c6f567590d8B469dbF4C8808e8ee32b8a45
 

Overview

ETH Balance

0.000001 ETH

Eth Value

Less Than $0.01 (@ $2,377.93/ETH)

Multichain Info

No addresses found
Transaction Hash
Method
Block
From
To
Set Refund Addre...176743322023-07-12 1:49:47594 days ago1689126587IN
0x69009c6f...ee32b8a45
0 ETH0.0004305213.95689456
Propose New Owne...176724202023-07-11 19:22:11594 days ago1689103331IN
0x69009c6f...ee32b8a45
0 ETH0.0016909224.23505543
Set Refund Addre...176723192023-07-11 19:01:23594 days ago1689102083IN
0x69009c6f...ee32b8a45
0 ETH0.0007640624.76943863
Transfer176412732023-07-07 10:16:11599 days ago1688724971IN
0x69009c6f...ee32b8a45
0.000001 ETH0.0003722917.68182852
Set Mirror Conne...176404762023-07-07 7:34:35599 days ago1688715275IN
0x69009c6f...ee32b8a45
0 ETH0.0012847126.95239993

Latest 25 internal transactions (View All)

Advanced mode:
Parent Transaction Hash Block
From
To
188125822023-12-18 11:28:59435 days ago1702898939
0x69009c6f...ee32b8a45
0.00022832 ETH
188125822023-12-18 11:28:59435 days ago1702898939
0x69009c6f...ee32b8a45
0.00022832 ETH
188119872023-12-18 9:28:59435 days ago1702891739
0x69009c6f...ee32b8a45
0.00022832 ETH
188119872023-12-18 9:28:59435 days ago1702891739
0x69009c6f...ee32b8a45
0.00022832 ETH
188114192023-12-18 7:33:47435 days ago1702884827
0x69009c6f...ee32b8a45
0.00022832 ETH
188114192023-12-18 7:33:47435 days ago1702884827
0x69009c6f...ee32b8a45
0.00022832 ETH
188108022023-12-18 5:29:11435 days ago1702877351
0x69009c6f...ee32b8a45
0.00022832 ETH
188108022023-12-18 5:29:11435 days ago1702877351
0x69009c6f...ee32b8a45
0.00022832 ETH
188102062023-12-18 3:29:11435 days ago1702870151
0x69009c6f...ee32b8a45
0.00022832 ETH
188102062023-12-18 3:29:11435 days ago1702870151
0x69009c6f...ee32b8a45
0.00022832 ETH
188096112023-12-18 1:29:23435 days ago1702862963
0x69009c6f...ee32b8a45
0.00022832 ETH
188096112023-12-18 1:29:23435 days ago1702862963
0x69009c6f...ee32b8a45
0.00022832 ETH
188090132023-12-17 23:29:11435 days ago1702855751
0x69009c6f...ee32b8a45
0.00022832 ETH
188090132023-12-17 23:29:11435 days ago1702855751
0x69009c6f...ee32b8a45
0.00022832 ETH
188060452023-12-17 13:29:11436 days ago1702819751
0x69009c6f...ee32b8a45
0.00023023 ETH
188060452023-12-17 13:29:11436 days ago1702819751
0x69009c6f...ee32b8a45
0.00023023 ETH
188054492023-12-17 11:28:59436 days ago1702812539
0x69009c6f...ee32b8a45
0.00023023 ETH
188054492023-12-17 11:28:59436 days ago1702812539
0x69009c6f...ee32b8a45
0.00023023 ETH
188048572023-12-17 9:29:11436 days ago1702805351
0x69009c6f...ee32b8a45
0.00023023 ETH
188048572023-12-17 9:29:11436 days ago1702805351
0x69009c6f...ee32b8a45
0.00023023 ETH
188042702023-12-17 7:29:11436 days ago1702798151
0x69009c6f...ee32b8a45
0.00023023 ETH
188042702023-12-17 7:29:11436 days ago1702798151
0x69009c6f...ee32b8a45
0.00023023 ETH
188036772023-12-17 5:29:11436 days ago1702790951
0x69009c6f...ee32b8a45
0.00023023 ETH
188036772023-12-17 5:29:11436 days ago1702790951
0x69009c6f...ee32b8a45
0.00023023 ETH
188030812023-12-17 3:29:11436 days ago1702783751
0x69009c6f...ee32b8a45
0.00023023 ETH
View All Internal Transactions
Loading...
Loading

Contract Source Code Verified (Exact Match)

Contract Name:
WormholeHubConnector

Compiler Version
v0.8.17+commit.8df45f5f

Optimization Enabled:
Yes with 200 runs

Other Settings:
default evmVersion, MIT license
File 1 of 11 : WormholeHubConnector.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {IRootManager} from "../../interfaces/IRootManager.sol";
import {IWormholeReceiver} from "../../interfaces/ambs/wormhole/IWormholeReceiver.sol";

import {HubConnector, Connector} from "../HubConnector.sol";

import {BaseWormhole} from "./BaseWormhole.sol";

contract WormholeHubConnector is HubConnector, BaseWormhole, IWormholeReceiver {
  // ============ Constructor ============
  constructor(
    uint32 _domain,
    uint32 _mirrorDomain,
    address _amb,
    address _rootManager,
    address _mirrorConnector,
    uint256 _gasCap,
    uint16 _mirrorWormholeChainId
  )
    HubConnector(_domain, _mirrorDomain, _amb, _rootManager, _mirrorConnector)
    BaseWormhole(_gasCap, _mirrorWormholeChainId)
  {}

  // ============ Override Fns ============
  function _verifySender(address _expected) internal view override returns (bool) {
    return _verifySender(mirrorConnector, _expected);
  }

  // ============ Public fns ============
  /**
   * @notice This function is called to receive messages through the wormhole relayer module
   * https://book.wormhole.com/technical/evm/relayer.html
   * @dev This is defined here instead of the `BaseWormhole` to avoid storing AMB values twice.
   */
  function receiveWormholeMessages(
    bytes memory _payload,
    bytes[] memory, // additionalVaas,
    bytes32 _sourceAddress,
    uint16 _sourceChain,
    bytes32 _deliveryHash
  ) public payable override {
    _wormholeSanityChecks(_sourceChain, AMB, _deliveryHash);

    _processMessageFrom(_fromWormholeFormat(_sourceAddress), _payload);
  }

  // ============ Private fns ============
  /**
   * @dev Handles an incoming `outboundRoot`
   */
  function _processMessageFrom(address _sender, bytes memory _data) internal override(BaseWormhole) {
    // enforce this came from connector on l2
    require(_verifySender(_sender), "!l2Connector");

    // get the data (should be the outbound root)
    require(_data.length == 32, "!length");

    // set the outbound root for BSC domain
    IRootManager(ROOT_MANAGER).aggregate(MIRROR_DOMAIN, bytes32(_data));

    emit MessageProcessed(_data, msg.sender);
  }

  function _sendMessage(bytes memory _data, bytes memory _encodedData) internal override {
    _sendMessage(AMB, mirrorConnector, _data, _encodedData);
  }
}

File 2 of 11 : Connector.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {ProposedOwnable} from "../../shared/ProposedOwnable.sol";
import {IConnector} from "../interfaces/IConnector.sol";

/**
 * @title Connector
 * @author Connext Labs, Inc.
 * @notice This contract has the messaging interface functions used by all connectors.
 *
 * @dev This contract stores information about mirror connectors, but can be used as a
 * base for contracts that do not have a mirror (i.e. the connector handling messaging on
 * mainnet). In this case, the `mirrorConnector` and `MIRROR_DOMAIN`
 * will be empty
 *
 * @dev If ownership is renounced, this contract will be unable to update its `mirrorConnector`
 * or `mirrorGas`
 */
abstract contract Connector is ProposedOwnable, IConnector {
  // ========== Custom Errors ===========

  error Connector__processMessage_notUsed();

  // ============ Events ============

  event NewConnector(
    uint32 indexed domain,
    uint32 indexed mirrorDomain,
    address amb,
    address rootManager,
    address mirrorConnector
  );

  event MirrorConnectorUpdated(address previous, address current);

  // ============ Public Storage ============

  /**
   * @notice The domain of this Messaging (i.e. Connector) contract.
   */
  uint32 public immutable DOMAIN;

  /**
   * @notice Address of the AMB on this domain.
   */
  address public immutable AMB;

  /**
   * @notice RootManager contract address.
   */
  address public immutable ROOT_MANAGER;

  /**
   * @notice The domain of the corresponding messaging (i.e. Connector) contract.
   */
  uint32 public immutable MIRROR_DOMAIN;

  /**
   * @notice Connector on L2 for L1 connectors, and vice versa.
   */
  address public mirrorConnector;

  // ============ Modifiers ============

  /**
   * @notice Errors if the msg.sender is not the registered AMB
   */
  modifier onlyAMB() {
    require(msg.sender == AMB, "!AMB");
    _;
  }

  /**
   * @notice Errors if the msg.sender is not the registered ROOT_MANAGER
   */
  modifier onlyRootManager() {
    // NOTE: RootManager will be zero address for spoke connectors.
    // Only root manager can dispatch a message to spokes/L2s via the hub connector.
    require(msg.sender == ROOT_MANAGER, "!rootManager");
    _;
  }

  // ============ Constructor ============

  /**
   * @notice Creates a new HubConnector instance
   * @dev The connectors are deployed such that there is one on each side of an AMB (i.e.
   * for optimism, there is one connector on optimism and one connector on mainnet)
   * @param _domain The domain this connector lives on
   * @param _mirrorDomain The spoke domain
   * @param _amb The address of the amb on the domain this connector lives on
   * @param _rootManager The address of the RootManager on mainnet
   * @param _mirrorConnector The address of the spoke connector
   */
  constructor(
    uint32 _domain,
    uint32 _mirrorDomain,
    address _amb,
    address _rootManager,
    address _mirrorConnector
  ) ProposedOwnable() {
    // set the owner
    _setOwner(msg.sender);

    // sanity checks on values
    require(_domain != 0, "empty domain");
    require(_rootManager != address(0), "empty rootManager");
    // see note at top of contract on why the mirror values are not sanity checked

    // set immutables
    DOMAIN = _domain;
    AMB = _amb;
    ROOT_MANAGER = _rootManager;
    MIRROR_DOMAIN = _mirrorDomain;
    // set mutables if defined
    if (_mirrorConnector != address(0)) {
      _setMirrorConnector(_mirrorConnector);
    }

    emit NewConnector(_domain, _mirrorDomain, _amb, _rootManager, _mirrorConnector);
  }

  // ============ Receivable ============
  /**
   * @notice Connectors may need to receive native asset to handle fees when sending a
   * message
   */
  receive() external payable {}

  // ============ Admin Functions ============

  /**
   * @notice Sets the address of the l2Connector for this domain
   */
  function setMirrorConnector(address _mirrorConnector) public onlyOwner {
    _setMirrorConnector(_mirrorConnector);
  }

  // ============ Public Functions ============

  /**
   * @notice Processes a message received by an AMB
   * @dev This is called by AMBs to process messages originating from mirror connector
   */
  function processMessage(bytes memory _data) external virtual onlyAMB {
    _processMessage(_data);
    emit MessageProcessed(_data, msg.sender);
  }

  /**
   * @notice Checks the cross domain sender for a given address
   */
  function verifySender(address _expected) external returns (bool) {
    return _verifySender(_expected);
  }

  // ============ Virtual Functions ============

  /**
   * @notice This function is used by the Connext contract on the l2 domain to send a message to the
   * l1 domain (i.e. called by Connext on optimism to send a message to mainnet with roots)
   * @param _data The contents of the message
   * @param _encodedData Data used to send the message; specific to connector
   */
  function _sendMessage(bytes memory _data, bytes memory _encodedData) internal virtual;

  /**
   * @notice This function is used by the AMBs to handle incoming messages. Should store the latest
   * root generated on the l2 domain.
   */
  function _processMessage(
    bytes memory /* _data */
  ) internal virtual {
    // By default, reverts. This is to ensure the call path is not used unless this function is
    // overridden by the inheriting class
    revert Connector__processMessage_notUsed();
  }

  /**
   * @notice Verify that the msg.sender is the correct AMB contract, and that the message's origin sender
   * is the expected address.
   * @dev Should be overridden by the implementing Connector contract.
   */
  function _verifySender(address _expected) internal virtual returns (bool);

  // ============ Private Functions ============

  function _setMirrorConnector(address _mirrorConnector) internal virtual {
    emit MirrorConnectorUpdated(mirrorConnector, _mirrorConnector);
    mirrorConnector = _mirrorConnector;
  }
}

File 3 of 11 : GasCap.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {ProposedOwnable} from "../../shared/ProposedOwnable.sol";

abstract contract GasCap is ProposedOwnable {
  // ============ Storage ============
  /**
   * @notice The gnosis amb requires destination gas to be specified on the origin.
   * The gas used will be passed in by the relayer to allow for real-time estimates,
   * but will be capped at the admin-set cap.
   */
  uint256 gasCap;

  // ============ Events ============

  /**
   * @notice Emitted when admin updates the gas cap
   * @param _previous The starting value
   * @param _updated The final value
   */
  event GasCapUpdated(uint256 _previous, uint256 _updated);

  // ============ Constructor ============
  constructor(uint256 _gasCap) {
    _setGasCap(_gasCap);
  }

  // ============ Admin Fns ============
  function setGasCap(uint256 _gasCap) public onlyOwner {
    _setGasCap(_gasCap);
  }

  // ============ Internal Fns ============

  /**
   * @notice Used (by admin) to update the gas cap
   * @param _gasCap The new value
   */
  function _setGasCap(uint256 _gasCap) internal {
    emit GasCapUpdated(gasCap, _gasCap);
    gasCap = _gasCap;
  }

  /**
   * @notice Used to get the gas to use. Will be the original value IFF it
   * is less than the cap
   * @param _gas The proposed gas value
   */
  function _getGas(uint256 _gas) internal view returns (uint256) {
    if (_gas > gasCap) {
      _gas = gasCap;
    }
    return _gas;
  }
}

File 4 of 11 : HubConnector.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {Connector} from "./Connector.sol";

/**
 * @title HubConnector
 * @author Connext Labs, Inc.
 * @notice This contract implements the messaging functions needed on the hub-side of a given AMB.
 * The HubConnector has a limited set of functionality compared to the SpokeConnector, namely that
 * it contains no logic to store or prove messages.
 *
 * @dev This contract should be deployed on the hub-side of an AMB (i.e. on L1), and contracts
 * which extend this should implement the virtual functions defined in the BaseConnector class
 */
abstract contract HubConnector is Connector {
  /**
   * @notice Creates a new HubConnector instance
   * @dev The connectors are deployed such that there is one on each side of an AMB (i.e.
   * for optimism, there is one connector on optimism and one connector on mainnet)
   * @param _domain The domain this connector lives on
   * @param _mirrorDomain The spoke domain
   * @param _amb The address of the amb on the domain this connector lives on
   * @param _rootManager The address of the RootManager on mainnet
   * @param _mirrorConnector The address of the spoke connector
   */
  constructor(
    uint32 _domain,
    uint32 _mirrorDomain,
    address _amb,
    address _rootManager,
    address _mirrorConnector
  ) Connector(_domain, _mirrorDomain, _amb, _rootManager, _mirrorConnector) {}

  // ============ Public fns ============
  /**
   * @notice Sends a message over the amb
   * @dev This is called by the root manager *only* on mainnet to propagate the aggregate root
   */
  function sendMessage(bytes memory _data, bytes memory _encodedData) external payable onlyRootManager {
    _sendMessage(_data, _encodedData);
    emit MessageSent(_data, _encodedData, msg.sender);
  }
}

File 5 of 11 : BaseWormhole.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {IWormholeRelayer} from "../../interfaces/ambs/wormhole/IWormholeRelayer.sol";

import {GasCap} from "../GasCap.sol";

abstract contract BaseWormhole is GasCap {
  // ============ Events ============

  event RefundAddressUpdated(address indexed previous, address indexed updated);

  // ============ Storage ============
  /**
   * @notice The wormhole id for the mirror network
   */
  uint16 public immutable MIRROR_WORMHOLE_ID;

  /**
   * @notice The address on this chain any refunds from wormhole fees will be
   * sent to
   */
  address public refundAddress;

  /**
   * @notice Mapping of processed messages from wormhole.
   * @dev Used for replay protection.
   */
  mapping(bytes32 => bool) public processedWhMessages;

  // ============ Constructor ============
  constructor(uint256 _gasCap, uint16 _mirrorWormholeChainId) GasCap(_gasCap) {
    MIRROR_WORMHOLE_ID = _mirrorWormholeChainId;
    _setRefundAddress(msg.sender);
  }

  // ============ Admin fns ============
  /**
   * @notice Allows the owner to set a new address to collect excess wormhole fees.
   * @param _updated The updated refund address
   */
  function setRefundAddress(address _updated) public onlyOwner {
    _setRefundAddress(_updated);
  }

  // ============ Public fns ============

  /**
   * @dev calculcate gas to call `receiveWormholeMessages` on target chain
   * https://github.com/wormhole-foundation/wormhole/blob/main/ethereum/contracts/relayer/deliveryProvider/DeliveryProvider.sol
   */
  function quoteEVMDeliveryPrice(uint256 _gasLimit, address _amb) public view returns (uint256 _cost) {
    // First Get the gas, if it is more than the cap use the cap
    // And calculcate delievery price with gasCap
    (_cost, ) = IWormholeRelayer(_amb).quoteEVMDeliveryPrice(MIRROR_WORMHOLE_ID, 0, _getGas(_gasLimit));
  }

  // ============ Private fns ============

  function _setRefundAddress(address _updated) internal {
    require(_updated != refundAddress, "!changed");
    emit RefundAddressUpdated(refundAddress, _updated);
    refundAddress = _updated;
  }

  /**
   * @dev Asserts the sender of a cross domain message
   */
  function _verifySender(address _mirrorConnector, address _expected) internal pure returns (bool) {
    return _mirrorConnector == _expected;
  }

  // DO NOT override _processMessage, should revert from `Connector` class. All messages must use the _processMessageFrom function
  /**
   * @notice This function is called to handle incoming messages. Should store the latest
   * root generated on the l2 domain.
   */
  function _processMessageFrom(address _sender, bytes memory _data) internal virtual;

  /**
   * @notice Performs sanity checks specific to receiving wormhole messages.
   * @dev Checks the sender is the AMB, the chain is the mirror, and replay.
   */
  function _wormholeSanityChecks(uint16 _sourceChain, address _amb, bytes32 _deliveryHash) internal {
    require(_sourceChain == MIRROR_WORMHOLE_ID, "!source chain");
    require(msg.sender == _amb, "!relayer");

    // Check that the VAA hasn't already been processed (replay protection)
    require(!processedWhMessages[_deliveryHash], "already processed");

    // Add the VAA to processed messages so it can't be replayed
    // you can alternatively rely on the replay protection
    // of something like transferWithPayload from the Token Bridge module
    processedWhMessages[_deliveryHash] = true;
  }

  /**
   * @dev send message via wormhole.
   * https://book.wormhole.com/technical/evm/relayer.html#sending-messages
   */
  function _sendMessage(
    address _amb,
    address _mirrorConnector,
    bytes memory _data,
    bytes memory _encodedData
  ) internal {
    // Should always be sending a merkle root
    require(_data.length == 32, "!data length");

    // Should include gas limit info in specialized calldata
    require(_encodedData.length == 32, "!encoded data length");

    //calculate cost to deliver message
    uint256 gasLimit = abi.decode(_encodedData, (uint256));
    uint256 deliveryCost = quoteEVMDeliveryPrice(gasLimit, _amb);
    require(deliveryCost == msg.value, "!msg.value");

    // publish delivery request
    IWormholeRelayer(_amb).sendPayloadToEvm{value: deliveryCost}(
      MIRROR_WORMHOLE_ID,
      _mirrorConnector,
      _data,
      0,
      gasLimit,
      MIRROR_WORMHOLE_ID, // refundChain
      refundAddress // refundAddress
    );
  }

  /**
   * @notice Converts from wormhole 32 byte identifier format to evm address
   */
  function _fromWormholeFormat(bytes32 _whFormatAddress) internal pure returns (address) {
    require(uint256(_whFormatAddress) >> 160 == 0, "!evm address");
    return address(uint160(uint256(_whFormatAddress)));
  }
}

File 6 of 11 : IConnector.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

import {IProposedOwnable} from "../../shared/interfaces/IProposedOwnable.sol";

/**
 * @notice This interface is what the Connext contract will send and receive messages through.
 * The messaging layer should conform to this interface, and should be interchangeable (i.e.
 * could be Nomad or a generic AMB under the hood).
 *
 * @dev This uses the nomad format to ensure nomad can be added in as it comes back online.
 *
 * Flow from transfer from polygon to optimism:
 * 1. User calls `xcall` with destination specified
 * 2. This will swap in to the bridge assets
 * 3. The swapped assets will get burned
 * 4. The Connext contract will call `dispatch` on the messaging contract to add the transfer
 *    to the root
 * 5. [At some time interval] Relayers call `send` to send the current root from polygon to
 *    mainnet. This is done on all "spoke" domains.
 * 6. [At some time interval] Relayers call `propagate` [better name] on mainnet, this generates a new merkle
 *    root from all of the AMBs
 *    - This function must be able to read root data from all AMBs and aggregate them into a single merkle
 *      tree root
 *    - Will send the mixed root from all chains back through the respective AMBs to all other chains
 * 7. AMB will call `update` to update the latest root on the messaging contract on spoke domains
 * 8. [At any point] Relayers can call `proveAndProcess` to prove inclusion of dispatched message, and call
 *    process on the `Connext` contract
 * 9. Takes minted bridge tokens and credits the LP
 *
 * AMB requirements:
 * - Access `msg.sender` both from mainnet -> spoke and vice versa
 * - Ability to read *our root* from the AMB
 *
 * AMBs:
 * - PoS bridge from polygon
 * - arbitrum bridge
 * - optimism bridge
 * - gnosis chain
 * - bsc (use multichain for messaging)
 */
interface IConnector is IProposedOwnable {
  // ============ Events ============
  /**
   * @notice Emitted whenever a message is successfully sent over an AMB
   * @param data The contents of the message
   * @param encodedData Data used to send the message; specific to connector
   * @param caller Who called the function (sent the message)
   */
  event MessageSent(bytes data, bytes encodedData, address caller);

  /**
   * @notice Emitted whenever a message is successfully received over an AMB
   * @param data The contents of the message
   * @param caller Who called the function
   */
  event MessageProcessed(bytes data, address caller);

  // ============ Public fns ============

  function processMessage(bytes memory _data) external;

  function verifySender(address _expected) external returns (bool);
}

File 7 of 11 : IRootManager.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity 0.8.17;

interface IRootManager {
  /**
   * @notice This is called by relayers to generate + send the mixed root from mainnet via AMB to
   * spoke domains.
   * @dev This must read information for the root from the registered AMBs.
   */
  function propagate(
    address[] calldata _connectors,
    uint256[] calldata _fees,
    bytes[] memory _encodedData
  ) external payable;

  /**
   * @notice Called by the connectors for various domains on the hub to aggregate their latest
   * inbound root.
   * @dev This must read information for the root from the registered AMBs
   */
  function aggregate(uint32 _domain, bytes32 _outbound) external;
}

File 8 of 11 : IWormholeReceiver.sol
// SPDX-License-Identifier: Apache 2

pragma solidity ^0.8.0;

/**
 * @notice Interface for a contract which can receive Wormhole messages.
 */
interface IWormholeReceiver {
  /**
   * @notice When a `send` is performed with this contract as the target, this function will be
   *     invoked by the WormholeRelayer contract
   *
   * NOTE: This function should be restricted such that only the Wormhole Relayer contract can call it.
   *
   * We also recommend that this function:
   *   - Stores all received `deliveryHash`s in a mapping `(bytes32 => bool)`, and
   *       on every call, checks that deliveryHash has not already been stored in the
   *       map (This is to prevent other users maliciously trying to relay the same message)
   *   - Checks that `sourceChain` and `sourceAddress` are indeed who
   *       you expect to have requested the calling of `send` or `forward` on the source chain
   *
   * The invocation of this function corresponding to the `send` request will have msg.value equal
   *   to the receiverValue specified in the send request.
   *
   * If the invocation of this function reverts or exceeds the gas limit
   *   specified by the send requester, this delivery will result in a `ReceiverFailure`.
   *
   * @param payload - an arbitrary message which was included in the delivery by the
   *     requester.
   * @param additionalVaas - Additional VAAs which were requested to be included in this delivery.
   *   They are guaranteed to all be included and in the same order as was specified in the
   *     delivery request.
   * @param sourceAddress - the (wormhole format) address on the sending chain which requested
   *     this delivery.
   * @param sourceChain - the wormhole chain ID where this delivery was requested.
   * @param deliveryHash - the VAA hash of the deliveryVAA.
   *
   * NOTE: These signedVaas are NOT verified by the Wormhole core contract prior to being provided
   *     to this call. Always make sure `parseAndVerify()` is called on the Wormhole core contract
   *     before trusting the content of a raw VAA, otherwise the VAA may be invalid or malicious.
   */
  function receiveWormholeMessages(
    bytes memory payload,
    bytes[] memory additionalVaas,
    bytes32 sourceAddress,
    uint16 sourceChain,
    bytes32 deliveryHash
  ) external payable;
}

File 9 of 11 : IWormholeRelayer.sol
// SPDX-License-Identifier: Apache 2

pragma solidity ^0.8.0;

/**
 * @title WormholeRelayer
 * @author
 * @notice This project allows developers to build cross-chain applications powered by Wormhole without needing to
 * write and run their own relaying infrastructure
 *
 * We implement the IWormholeRelayer interface that allows users to request a delivery provider to relay a payload (and/or additional VAAs)
 * to a chain and address of their choice.
 */

/**
 * @notice VaaKey identifies a wormhole message
 *
 * @custom:member chainId Wormhole chain ID of the chain where this VAA was emitted from
 * @custom:member emitterAddress Address of the emitter of the VAA, in Wormhole bytes32 format
 * @custom:member sequence Sequence number of the VAA
 */
struct VaaKey {
  uint16 chainId;
  bytes32 emitterAddress;
  uint64 sequence;
}

interface IWormholeRelayerBase {
  event SendEvent(uint64 indexed sequence, uint256 deliveryQuote, uint256 paymentForExtraReceiverValue);

  function getRegisteredWormholeRelayerContract(uint16 chainId) external view returns (bytes32);
}

/**
 * @title IWormholeRelayerSend
 * @notice The interface to request deliveries
 */
interface IWormholeRelayerSend is IWormholeRelayerBase {
  /**
   * @notice Publishes an instruction for the default delivery provider
   * to relay a payload to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and `msg.value` equal to `receiverValue`
   *
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to `quoteEVMDeliveryPrice(targetChain, receiverValue, gasLimit)`
   *
   * Any refunds (from leftover gas) will be paid to the delivery provider. In order to receive the refunds, use the `sendPayloadToEvm` function
   * with `refundChain` and `refundAddress` as parameters
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver)
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function sendPayloadToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit
  ) external payable returns (uint64 sequence);

  /**
   * @notice Publishes an instruction for the default delivery provider
   * to relay a payload to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and `msg.value` equal to `receiverValue`
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to `quoteEVMDeliveryPrice(targetChain, receiverValue, gasLimit)`
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver)
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`. Any units of gas unused will be refunded according to the
   *        `targetChainRefundPerGasUnused` rate quoted by the delivery provider
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function sendPayloadToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit,
    uint16 refundChain,
    address refundAddress
  ) external payable returns (uint64 sequence);

  /**
   * @notice Publishes an instruction for the default delivery provider
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and `msg.value` equal to `receiverValue`
   *
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to `quoteEVMDeliveryPrice(targetChain, receiverValue, gasLimit)`
   *
   * Any refunds (from leftover gas) will be paid to the delivery provider. In order to receive the refunds, use the `sendVaasToEvm` function
   * with `refundChain` and `refundAddress` as parameters
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver)
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function sendVaasToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit,
    VaaKey[] memory vaaKeys
  ) external payable returns (uint64 sequence);

  /**
   * @notice Publishes an instruction for the default delivery provider
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and `msg.value` equal to `receiverValue`
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to `quoteEVMDeliveryPrice(targetChain, receiverValue, gasLimit)`
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver)
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`. Any units of gas unused will be refunded according to the
   *        `targetChainRefundPerGasUnused` rate quoted by the delivery provider
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function sendVaasToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit,
    VaaKey[] memory vaaKeys,
    uint16 refundChain,
    address refundAddress
  ) external payable returns (uint64 sequence);

  /**
   * @notice Publishes an instruction for the delivery provider at `deliveryProviderAddress`
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and `msg.value` equal to
   * receiverValue + (arbitrary amount that is paid for by paymentForExtraReceiverValue of this chain's wei) in targetChain wei.
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to
   * quoteEVMDeliveryPrice(targetChain, receiverValue, gasLimit, deliveryProviderAddress) + paymentForExtraReceiverValue
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver)
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param paymentForExtraReceiverValue amount (in current chain currency units) to spend on extra receiverValue
   *        (in addition to the `receiverValue` specified)
   * @param gasLimit gas limit with which to call `targetAddress`. Any units of gas unused will be refunded according to the
   *        `targetChainRefundPerGasUnused` rate quoted by the delivery provider
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @param consistencyLevel Consistency level with which to publish the delivery instructions - see
   *        https://book.wormhole.com/wormhole/3_coreLayerContracts.html?highlight=consistency#consistency-levels
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function sendToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 paymentForExtraReceiverValue,
    uint256 gasLimit,
    uint16 refundChain,
    address refundAddress,
    address deliveryProviderAddress,
    VaaKey[] memory vaaKeys,
    uint8 consistencyLevel
  ) external payable returns (uint64 sequence);

  /**
   * @notice Publishes an instruction for the delivery provider at `deliveryProviderAddress`
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with `msg.value` equal to
   * receiverValue + (arbitrary amount that is paid for by paymentForExtraReceiverValue of this chain's wei) in targetChain wei.
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * This function must be called with `msg.value` equal to
   * quoteDeliveryPrice(targetChain, receiverValue, encodedExecutionParameters, deliveryProviderAddress) + paymentForExtraReceiverValue
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver), in Wormhole bytes32 format
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param paymentForExtraReceiverValue amount (in current chain currency units) to spend on extra receiverValue
   *        (in addition to the `receiverValue` specified)
   * @param encodedExecutionParameters encoded information on how to execute delivery that may impact pricing
   *        e.g. for version EVM_V1, this is a struct that encodes the `gasLimit` with which to call `targetAddress`
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to, in Wormhole bytes32 format
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @param consistencyLevel Consistency level with which to publish the delivery instructions - see
   *        https://book.wormhole.com/wormhole/3_coreLayerContracts.html?highlight=consistency#consistency-levels
   * @return sequence sequence number of published VAA containing delivery instructions
   */
  function send(
    uint16 targetChain,
    bytes32 targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 paymentForExtraReceiverValue,
    bytes memory encodedExecutionParameters,
    uint16 refundChain,
    bytes32 refundAddress,
    address deliveryProviderAddress,
    VaaKey[] memory vaaKeys,
    uint8 consistencyLevel
  ) external payable returns (uint64 sequence);

  /**
   * @notice Performs the same function as a `send`, except:
   * 1)  Can only be used during a delivery (i.e. in execution of `receiveWormholeMessages`)
   * 2)  Is paid for (along with any other calls to forward) by (any msg.value passed in) + (refund leftover from current delivery)
   * 3)  Only executes after `receiveWormholeMessages` is completed (and thus does not return a sequence number)
   *
   * The refund from the delivery currently in progress will not be sent to the user; it will instead
   * be paid to the delivery provider to perform the instruction specified here
   *
   * Publishes an instruction for the same delivery provider (or default, if the same one doesn't support the new target chain)
   * to relay a payload to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and with `msg.value` equal to `receiverValue`
   *
   * The following equation must be satisfied (sum_f indicates summing over all forwards requested in `receiveWormholeMessages`):
   * (refund amount from current execution of receiveWormholeMessages) + sum_f [msg.value_f]
   * >= sum_f [quoteEVMDeliveryPrice(targetChain_f, receiverValue_f, gasLimit_f)]
   *
   * The difference between the two sides of the above inequality will be added to `paymentForExtraReceiverValue` of the first forward requested
   *
   * Any refunds (from leftover gas) from this forward will be paid to the same refundChain and refundAddress specified for the current delivery.
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver), in Wormhole bytes32 format
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   */
  function forwardPayloadToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit
  ) external payable;

  /**
   * @notice Performs the same function as a `send`, except:
   * 1)  Can only be used during a delivery (i.e. in execution of `receiveWormholeMessages`)
   * 2)  Is paid for (along with any other calls to forward) by (any msg.value passed in) + (refund leftover from current delivery)
   * 3)  Only executes after `receiveWormholeMessages` is completed (and thus does not return a sequence number)
   *
   * The refund from the delivery currently in progress will not be sent to the user; it will instead
   * be paid to the delivery provider to perform the instruction specified here
   *
   * Publishes an instruction for the same delivery provider (or default, if the same one doesn't support the new target chain)
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and with `msg.value` equal to `receiverValue`
   *
   * The following equation must be satisfied (sum_f indicates summing over all forwards requested in `receiveWormholeMessages`):
   * (refund amount from current execution of receiveWormholeMessages) + sum_f [msg.value_f]
   * >= sum_f [quoteEVMDeliveryPrice(targetChain_f, receiverValue_f, gasLimit_f)]
   *
   * The difference between the two sides of the above inequality will be added to `paymentForExtraReceiverValue` of the first forward requested
   *
   * Any refunds (from leftover gas) from this forward will be paid to the same refundChain and refundAddress specified for the current delivery.
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver), in Wormhole bytes32 format
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   */
  function forwardVaasToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 gasLimit,
    VaaKey[] memory vaaKeys
  ) external payable;

  /**
   * @notice Performs the same function as a `send`, except:
   * 1)  Can only be used during a delivery (i.e. in execution of `receiveWormholeMessages`)
   * 2)  Is paid for (along with any other calls to forward) by (any msg.value passed in) + (refund leftover from current delivery)
   * 3)  Only executes after `receiveWormholeMessages` is completed (and thus does not return a sequence number)
   *
   * The refund from the delivery currently in progress will not be sent to the user; it will instead
   * be paid to the delivery provider to perform the instruction specified here
   *
   * Publishes an instruction for the delivery provider at `deliveryProviderAddress`
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with gas limit `gasLimit` and with `msg.value` equal to
   * receiverValue + (arbitrary amount that is paid for by paymentForExtraReceiverValue of this chain's wei) in targetChain wei.
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * The following equation must be satisfied (sum_f indicates summing over all forwards requested in `receiveWormholeMessages`):
   * (refund amount from current execution of receiveWormholeMessages) + sum_f [msg.value_f]
   * >= sum_f [quoteEVMDeliveryPrice(targetChain_f, receiverValue_f, gasLimit_f, deliveryProviderAddress_f) + paymentForExtraReceiverValue_f]
   *
   * The difference between the two sides of the above inequality will be added to `paymentForExtraReceiverValue` of the first forward requested
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver), in Wormhole bytes32 format
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param paymentForExtraReceiverValue amount (in current chain currency units) to spend on extra receiverValue
   *        (in addition to the `receiverValue` specified)
   * @param gasLimit gas limit with which to call `targetAddress`. Any units of gas unused will be refunded according to the
   *        `targetChainRefundPerGasUnused` rate quoted by the delivery provider
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to, in Wormhole bytes32 format
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @param consistencyLevel Consistency level with which to publish the delivery instructions - see
   *        https://book.wormhole.com/wormhole/3_coreLayerContracts.html?highlight=consistency#consistency-levels
   */
  function forwardToEvm(
    uint16 targetChain,
    address targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 paymentForExtraReceiverValue,
    uint256 gasLimit,
    uint16 refundChain,
    address refundAddress,
    address deliveryProviderAddress,
    VaaKey[] memory vaaKeys,
    uint8 consistencyLevel
  ) external payable;

  /**
   * @notice Performs the same function as a `send`, except:
   * 1)  Can only be used during a delivery (i.e. in execution of `receiveWormholeMessages`)
   * 2)  Is paid for (along with any other calls to forward) by (any msg.value passed in) + (refund leftover from current delivery)
   * 3)  Only executes after `receiveWormholeMessages` is completed (and thus does not return a sequence number)
   *
   * The refund from the delivery currently in progress will not be sent to the user; it will instead
   * be paid to the delivery provider to perform the instruction specified here
   *
   * Publishes an instruction for the delivery provider at `deliveryProviderAddress`
   * to relay a payload and VAAs specified by `vaaKeys` to the address `targetAddress` on chain `targetChain`
   * with `msg.value` equal to
   * receiverValue + (arbitrary amount that is paid for by paymentForExtraReceiverValue of this chain's wei) in targetChain wei.
   *
   * Any refunds (from leftover gas) will be sent to `refundAddress` on chain `refundChain`
   * `targetAddress` must implement the IWormholeReceiver interface
   *
   * The following equation must be satisfied (sum_f indicates summing over all forwards requested in `receiveWormholeMessages`):
   * (refund amount from current execution of receiveWormholeMessages) + sum_f [msg.value_f]
   * >= sum_f [quoteDeliveryPrice(targetChain_f, receiverValue_f, encodedExecutionParameters_f, deliveryProviderAddress_f) + paymentForExtraReceiverValue_f]
   *
   * The difference between the two sides of the above inequality will be added to `paymentForExtraReceiverValue` of the first forward requested
   *
   * @param targetChain in Wormhole Chain ID format
   * @param targetAddress address to call on targetChain (that implements IWormholeReceiver), in Wormhole bytes32 format
   * @param payload arbitrary bytes to pass in as parameter in call to `targetAddress`
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param paymentForExtraReceiverValue amount (in current chain currency units) to spend on extra receiverValue
   *        (in addition to the `receiverValue` specified)
   * @param encodedExecutionParameters encoded information on how to execute delivery that may impact pricing
   *        e.g. for version EVM_V1, this is a struct that encodes the `gasLimit` with which to call `targetAddress`
   * @param refundChain The chain to deliver any refund to, in Wormhole Chain ID format
   * @param refundAddress The address on `refundChain` to deliver any refund to, in Wormhole bytes32 format
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @param vaaKeys Additional VAAs to pass in as parameter in call to `targetAddress`
   * @param consistencyLevel Consistency level with which to publish the delivery instructions - see
   *        https://book.wormhole.com/wormhole/3_coreLayerContracts.html?highlight=consistency#consistency-levels
   */
  function forward(
    uint16 targetChain,
    bytes32 targetAddress,
    bytes memory payload,
    uint256 receiverValue,
    uint256 paymentForExtraReceiverValue,
    bytes memory encodedExecutionParameters,
    uint16 refundChain,
    bytes32 refundAddress,
    address deliveryProviderAddress,
    VaaKey[] memory vaaKeys,
    uint8 consistencyLevel
  ) external payable;

  /**
   * @notice Requests a previously published delivery instruction to be redelivered
   * (e.g. with a different delivery provider)
   *
   * This function must be called with `msg.value` equal to
   * quoteEVMDeliveryPrice(targetChain, newReceiverValue, newGasLimit, newDeliveryProviderAddress)
   *
   * @param deliveryVaaKey VaaKey identifying the wormhole message containing the
   *        previously published delivery instructions
   * @param targetChain The target chain that the original delivery targeted. Must match targetChain from original delivery instructions
   * @param newReceiverValue new msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param newGasLimit gas limit with which to call `targetAddress`. Any units of gas unused will be refunded according to the
   *        `targetChainRefundPerGasUnused` rate quoted by the delivery provider, to the refund chain and address specified in the original request
   * @param newDeliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @return sequence sequence number of published VAA containing redelivery instructions
   */
  function resendToEvm(
    VaaKey memory deliveryVaaKey,
    uint16 targetChain,
    uint256 newReceiverValue,
    uint256 newGasLimit,
    address newDeliveryProviderAddress
  ) external payable returns (uint64 sequence);

  /**
   * @notice Requests a previously published delivery instruction to be redelivered
   *
   *
   * This function must be called with `msg.value` equal to
   * quoteDeliveryPrice(targetChain, newReceiverValue, newEncodedExecutionParameters, newDeliveryProviderAddress)
   *
   * @param deliveryVaaKey VaaKey identifying the wormhole message containing the
   *        previously published delivery instructions
   * @param targetChain The target chain that the original delivery targeted. Must match targetChain from original delivery instructions
   * @param newReceiverValue new msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param newEncodedExecutionParameters new encoded information on how to execute delivery that may impact pricing
   *        e.g. for version EVM_V1, this is a struct that encodes the `gasLimit` with which to call `targetAddress`
   * @param newDeliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @return sequence sequence number of published VAA containing redelivery instructions
   */
  function resend(
    VaaKey memory deliveryVaaKey,
    uint16 targetChain,
    uint256 newReceiverValue,
    bytes memory newEncodedExecutionParameters,
    address newDeliveryProviderAddress
  ) external payable returns (uint64 sequence);

  /**
   * @notice Returns the price to request a relay to chain `targetChain`, using the default delivery provider
   *
   * @param targetChain in Wormhole Chain ID format
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   * @return nativePriceQuote Price, in units of current chain currency, that the delivery provider charges to perform the relay
   * @return targetChainRefundPerGasUnused amount of target chain currency that will be refunded per unit of gas unused,
   *         if a refundAddress is specified
   */
  function quoteEVMDeliveryPrice(
    uint16 targetChain,
    uint256 receiverValue,
    uint256 gasLimit
  ) external view returns (uint256 nativePriceQuote, uint256 targetChainRefundPerGasUnused);

  /**
   * @notice Returns the price to request a relay to chain `targetChain`, using delivery provider `deliveryProviderAddress`
   *
   * @param targetChain in Wormhole Chain ID format
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param gasLimit gas limit with which to call `targetAddress`.
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @return nativePriceQuote Price, in units of current chain currency, that the delivery provider charges to perform the relay
   * @return targetChainRefundPerGasUnused amount of target chain currency that will be refunded per unit of gas unused,
   *         if a refundAddress is specified
   */
  function quoteEVMDeliveryPrice(
    uint16 targetChain,
    uint256 receiverValue,
    uint256 gasLimit,
    address deliveryProviderAddress
  ) external view returns (uint256 nativePriceQuote, uint256 targetChainRefundPerGasUnused);

  /**
   * @notice Returns the price to request a relay to chain `targetChain`, using delivery provider `deliveryProviderAddress`
   *
   * @param targetChain in Wormhole Chain ID format
   * @param receiverValue msg.value that delivery provider should pass in for call to `targetAddress` (in targetChain currency units)
   * @param encodedExecutionParameters encoded information on how to execute delivery that may impact pricing
   *        e.g. for version EVM_V1, this is a struct that encodes the `gasLimit` with which to call `targetAddress`
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @return nativePriceQuote Price, in units of current chain currency, that the delivery provider charges to perform the relay
   * @return encodedExecutionInfo encoded information on how the delivery will be executed
   *        e.g. for version EVM_V1, this is a struct that encodes the `gasLimit` and `targetChainRefundPerGasUnused`
   *             (which is the amount of target chain currency that will be refunded per unit of gas unused,
   *              if a refundAddress is specified)
   */
  function quoteDeliveryPrice(
    uint16 targetChain,
    uint256 receiverValue,
    bytes memory encodedExecutionParameters,
    address deliveryProviderAddress
  ) external view returns (uint256 nativePriceQuote, bytes memory encodedExecutionInfo);

  /**
   * @notice Returns the (extra) amount of target chain currency that `targetAddress`
   * will be called with, if the `paymentForExtraReceiverValue` field is set to `currentChainAmount`
   *
   * @param targetChain in Wormhole Chain ID format
   * @param currentChainAmount The value that `paymentForExtraReceiverValue` will be set to
   * @param deliveryProviderAddress The address of the desired delivery provider's implementation of IDeliveryProvider
   * @return targetChainAmount The amount such that if `targetAddress` will be called with `msg.value` equal to
   *         receiverValue + targetChainAmount
   */
  function quoteNativeForChain(
    uint16 targetChain,
    uint256 currentChainAmount,
    address deliveryProviderAddress
  ) external view returns (uint256 targetChainAmount);

  /**
   * @notice Returns the address of the current default delivery provider
   * @return deliveryProvider The address of (the default delivery provider)'s contract on this source
   *   chain. This must be a contract that implements IDeliveryProvider.
   */
  function getDefaultDeliveryProvider() external view returns (address deliveryProvider);
}

/**
 * @title IWormholeRelayerDelivery
 * @notice The interface to execute deliveries. Only relevant for Delivery Providers
 */
interface IWormholeRelayerDelivery is IWormholeRelayerBase {
  enum DeliveryStatus {
    SUCCESS,
    RECEIVER_FAILURE,
    FORWARD_REQUEST_FAILURE,
    FORWARD_REQUEST_SUCCESS
  }

  enum RefundStatus {
    REFUND_SENT,
    REFUND_FAIL,
    CROSS_CHAIN_REFUND_SENT,
    CROSS_CHAIN_REFUND_FAIL_PROVIDER_NOT_SUPPORTED,
    CROSS_CHAIN_REFUND_FAIL_NOT_ENOUGH
  }

  /**
   * @custom:member recipientContract - The target contract address
   * @custom:member sourceChain - The chain which this delivery was requested from (in wormhole
   *     ChainID format)
   * @custom:member sequence - The wormhole sequence number of the delivery VAA on the source chain
   *     corresponding to this delivery request
   * @custom:member deliveryVaaHash - The hash of the delivery VAA corresponding to this delivery
   *     request
   * @custom:member gasUsed - The amount of gas that was used to call your target contract
   * @custom:member status:
   *   - RECEIVER_FAILURE, if the target contract reverts
   *   - SUCCESS, if the target contract doesn't revert and no forwards were requested
   *   - FORWARD_REQUEST_FAILURE, if the target contract doesn't revert, forwards were requested,
   *       but provided/leftover funds were not sufficient to cover them all
   *   - FORWARD_REQUEST_SUCCESS, if the target contract doesn't revert and all forwards are covered
   * @custom:member additionalStatusInfo:
   *   - If status is SUCCESS or FORWARD_REQUEST_SUCCESS, then this is empty.
   *   - If status is RECEIVER_FAILURE, this is `RETURNDATA_TRUNCATION_THRESHOLD` bytes of the
   *       return data (i.e. potentially truncated revert reason information).
   *   - If status is FORWARD_REQUEST_FAILURE, this is also the revert data - the reason the forward failed.
   *     This will be either an encoded Cancelled, DeliveryProviderReverted, or DeliveryProviderPaymentFailed error
   * @custom:member refundStatus - Result of the refund. REFUND_SUCCESS or REFUND_FAIL are for
   *     refunds where targetChain=refundChain; the others are for targetChain!=refundChain,
   *     where a cross chain refund is necessary
   * @custom:member overridesInfo:
   *   - If not an override: empty bytes array
   *   - Otherwise: An encoded `DeliveryOverride`
   */
  event Delivery(
    address indexed recipientContract,
    uint16 indexed sourceChain,
    uint64 indexed sequence,
    bytes32 deliveryVaaHash,
    DeliveryStatus status,
    uint256 gasUsed,
    RefundStatus refundStatus,
    bytes additionalStatusInfo,
    bytes overridesInfo
  );

  /**
   * @notice The delivery provider calls `deliver` to relay messages as described by one delivery instruction
   *
   * The delivery provider must pass in the specified (by VaaKeys[]) signed wormhole messages (VAAs) from the source chain
   * as well as the signed wormhole message with the delivery instructions (the delivery VAA)
   *
   * The messages will be relayed to the target address (with the specified gas limit and receiver value) iff the following checks are met:
   * - the delivery VAA has a valid signature
   * - the delivery VAA's emitter is one of these WormholeRelayer contracts
   * - the delivery provider passed in at least enough of this chain's currency as msg.value (enough meaning the maximum possible refund)
   * - the instruction's target chain is this chain
   * - the relayed signed VAAs match the descriptions in container.messages (the VAA hashes match, or the emitter address, sequence number pair matches, depending on the description given)
   *
   * @param encodedVMs - An array of signed wormhole messages (all from the same source chain
   *     transaction)
   * @param encodedDeliveryVAA - Signed wormhole message from the source chain's WormholeRelayer
   *     contract with payload being the encoded delivery instruction container
   * @param relayerRefundAddress - The address to which any refunds to the delivery provider
   *     should be sent
   * @param deliveryOverrides - Optional overrides field which must be either an empty bytes array or
   *     an encoded DeliveryOverride struct
   */
  function deliver(
    bytes[] memory encodedVMs,
    bytes memory encodedDeliveryVAA,
    address payable relayerRefundAddress,
    bytes memory deliveryOverrides
  ) external payable;
}

interface IWormholeRelayer is IWormholeRelayerDelivery, IWormholeRelayerSend {}

/*
 *  Errors thrown by IWormholeRelayer contract
 */

// Bound chosen by the following formula: `memoryWord * 4 + selectorSize`.
// This means that an error identifier plus four fixed size arguments should be available to developers.
// In the case of a `require` revert with error message, this should provide 2 memory word's worth of data.
uint256 constant RETURNDATA_TRUNCATION_THRESHOLD = 132;

//When msg.value was not equal to `delivery provider's quoted delivery price` + `paymentForExtraReceiverValue`
error InvalidMsgValue(uint256 msgValue, uint256 totalFee);

error RequestedGasLimitTooLow();

error DeliveryProviderDoesNotSupportTargetChain(address relayer, uint16 chainId);
error DeliveryProviderCannotReceivePayment();

//When calling `forward()` on the WormholeRelayer if no delivery is in progress
error NoDeliveryInProgress();
//When calling `delivery()` a second time even though a delivery is already in progress
error ReentrantDelivery(address msgSender, address lockedBy);
//When any other contract but the delivery target calls `forward()` on the WormholeRelayer while a
//  delivery is in progress
error ForwardRequestFromWrongAddress(address msgSender, address deliveryTarget);

error InvalidPayloadId(uint8 parsed, uint8 expected);
error InvalidPayloadLength(uint256 received, uint256 expected);
error InvalidVaaKeyType(uint8 parsed);

error InvalidDeliveryVaa(string reason);
//When the delivery VAA (signed wormhole message with delivery instructions) was not emitted by the
//  registered WormholeRelayer contract
error InvalidEmitter(bytes32 emitter, bytes32 registered, uint16 chainId);
error VaaKeysLengthDoesNotMatchVaasLength(uint256 keys, uint256 vaas);
error VaaKeysDoNotMatchVaas(uint8 index);
//When someone tries to call an external function of the WormholeRelayer that is only intended to be
//  called by the WormholeRelayer itself (to allow retroactive reverts for atomicity)
error RequesterNotWormholeRelayer();

//When trying to relay a `DeliveryInstruction` to any other chain but the one it was specified for
error TargetChainIsNotThisChain(uint16 targetChain);
error ForwardNotSufficientlyFunded(uint256 amountOfFunds, uint256 amountOfFundsNeeded);
//When a `DeliveryOverride` contains a gas limit that's less than the original
error InvalidOverrideGasLimit();
//When a `DeliveryOverride` contains a receiver value that's less than the original
error InvalidOverrideReceiverValue();
//When a `DeliveryOverride` contains a 'refund per unit of gas unused' that's less than the original
error InvalidOverrideRefundPerGasUnused();

//When the delivery provider doesn't pass in sufficient funds (i.e. msg.value does not cover the
// maximum possible refund to the user)
error InsufficientRelayerFunds(uint256 msgValue, uint256 minimum);

//When a bytes32 field can't be converted into a 20 byte EVM address, because the 12 padding bytes
//  are non-zero (duplicated from Utils.sol)
error NotAnEvmAddress(bytes32);

File 10 of 11 : ProposedOwnable.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity 0.8.17;

import {IProposedOwnable} from "./interfaces/IProposedOwnable.sol";

/**
 * @title ProposedOwnable
 * @notice 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 via a two step process:
 * 1. Call `proposeOwner`
 * 2. Wait out the delay period
 * 3. Call `acceptOwner`
 *
 * @dev 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.
 *
 * @dev The majority of this code was taken from the openzeppelin Ownable
 * contract
 *
 */
abstract contract ProposedOwnable is IProposedOwnable {
  // ========== Custom Errors ===========

  error ProposedOwnable__onlyOwner_notOwner();
  error ProposedOwnable__onlyProposed_notProposedOwner();
  error ProposedOwnable__ownershipDelayElapsed_delayNotElapsed();
  error ProposedOwnable__proposeNewOwner_invalidProposal();
  error ProposedOwnable__proposeNewOwner_noOwnershipChange();
  error ProposedOwnable__renounceOwnership_noProposal();
  error ProposedOwnable__renounceOwnership_invalidProposal();

  // ============ Properties ============

  address private _owner;

  address private _proposed;
  uint256 private _proposedOwnershipTimestamp;

  uint256 private constant _delay = 7 days;

  // ======== Getters =========

  /**
   * @notice Returns the address of the current owner.
   */
  function owner() public view virtual returns (address) {
    return _owner;
  }

  /**
   * @notice Returns the address of the proposed owner.
   */
  function proposed() public view virtual returns (address) {
    return _proposed;
  }

  /**
   * @notice Returns the address of the proposed owner.
   */
  function proposedTimestamp() public view virtual returns (uint256) {
    return _proposedOwnershipTimestamp;
  }

  /**
   * @notice Returns the delay period before a new owner can be accepted.
   */
  function delay() public view virtual returns (uint256) {
    return _delay;
  }

  /**
   * @notice Throws if called by any account other than the owner.
   */
  modifier onlyOwner() {
    if (_owner != msg.sender) revert ProposedOwnable__onlyOwner_notOwner();
    _;
  }

  /**
   * @notice Throws if called by any account other than the proposed owner.
   */
  modifier onlyProposed() {
    if (_proposed != msg.sender) revert ProposedOwnable__onlyProposed_notProposedOwner();
    _;
  }

  /**
   * @notice Throws if the ownership delay has not elapsed
   */
  modifier ownershipDelayElapsed() {
    // Ensure delay has elapsed
    if ((block.timestamp - _proposedOwnershipTimestamp) <= _delay)
      revert ProposedOwnable__ownershipDelayElapsed_delayNotElapsed();
    _;
  }

  /**
   * @notice Indicates if the ownership has been renounced() by
   * checking if current owner is address(0)
   */
  function renounced() public view returns (bool) {
    return _owner == address(0);
  }

  // ======== External =========

  /**
   * @notice Sets the timestamp for an owner to be proposed, and sets the
   * newly proposed owner as step 1 in a 2-step process
   */
  function proposeNewOwner(address newlyProposed) public virtual onlyOwner {
    // Contract as source of truth
    if (_proposed == newlyProposed && _proposedOwnershipTimestamp != 0)
      revert ProposedOwnable__proposeNewOwner_invalidProposal();

    // Sanity check: reasonable proposal
    if (_owner == newlyProposed) revert ProposedOwnable__proposeNewOwner_noOwnershipChange();

    _setProposed(newlyProposed);
  }

  /**
   * @notice Renounces ownership of the contract after a delay
   */
  function renounceOwnership() public virtual onlyOwner ownershipDelayElapsed {
    // Ensure there has been a proposal cycle started
    if (_proposedOwnershipTimestamp == 0) revert ProposedOwnable__renounceOwnership_noProposal();

    // Require proposed is set to 0
    if (_proposed != address(0)) revert ProposedOwnable__renounceOwnership_invalidProposal();

    // Emit event, set new owner, reset timestamp
    _setOwner(address(0));
  }

  /**
   * @notice Transfers ownership of the contract to a new account (`newOwner`).
   * Can only be called by the current owner.
   */
  function acceptProposedOwner() public virtual onlyProposed ownershipDelayElapsed {
    // NOTE: no need to check if _owner == _proposed, because the _proposed
    // is 0-d out and this check is implicitly enforced by modifier

    // NOTE: no need to check if _proposedOwnershipTimestamp > 0 because
    // the only time this would happen is if the _proposed was never
    // set (will fail from modifier) or if the owner == _proposed (checked
    // above)

    // Emit event, set new owner, reset timestamp
    _setOwner(_proposed);
  }

  // ======== Internal =========

  function _setOwner(address newOwner) internal {
    emit OwnershipTransferred(_owner, newOwner);
    _owner = newOwner;
    delete _proposedOwnershipTimestamp;
    delete _proposed;
  }

  function _setProposed(address newlyProposed) private {
    _proposedOwnershipTimestamp = block.timestamp;
    _proposed = newlyProposed;
    emit OwnershipProposed(newlyProposed);
  }
}

File 11 of 11 : IProposedOwnable.sol
// SPDX-License-Identifier: MIT
pragma solidity 0.8.17;

/**
 * @title IProposedOwnable
 * @notice Defines a minimal interface for ownership with a two step proposal and acceptance
 * process
 */
interface IProposedOwnable {
  /**
   * @dev This emits when change in ownership of a contract is proposed.
   */
  event OwnershipProposed(address indexed proposedOwner);

  /**
   * @dev This emits when ownership of a contract changes.
   */
  event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);

  /**
   * @notice Get the address of the owner
   * @return owner_ The address of the owner.
   */
  function owner() external view returns (address owner_);

  /**
   * @notice Get the address of the proposed owner
   * @return proposed_ The address of the proposed.
   */
  function proposed() external view returns (address proposed_);

  /**
   * @notice Set the address of the proposed owner of the contract
   * @param newlyProposed The proposed new owner of the contract
   */
  function proposeNewOwner(address newlyProposed) external;

  /**
   * @notice Set the address of the proposed owner of the contract
   */
  function acceptProposedOwner() external;
}

Settings
{
  "evmVersion": "london",
  "libraries": {},
  "metadata": {
    "bytecodeHash": "ipfs",
    "useLiteralContent": true
  },
  "optimizer": {
    "enabled": true,
    "runs": 200
  },
  "remappings": [],
  "outputSelection": {
    "*": {
      "*": [
        "evm.bytecode",
        "evm.deployedBytecode",
        "devdoc",
        "userdoc",
        "metadata",
        "abi"
      ]
    }
  }
}

Contract Security Audit

Contract ABI

[{"inputs":[{"internalType":"uint32","name":"_domain","type":"uint32"},{"internalType":"uint32","name":"_mirrorDomain","type":"uint32"},{"internalType":"address","name":"_amb","type":"address"},{"internalType":"address","name":"_rootManager","type":"address"},{"internalType":"address","name":"_mirrorConnector","type":"address"},{"internalType":"uint256","name":"_gasCap","type":"uint256"},{"internalType":"uint16","name":"_mirrorWormholeChainId","type":"uint16"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"Connector__processMessage_notUsed","type":"error"},{"inputs":[],"name":"ProposedOwnable__onlyOwner_notOwner","type":"error"},{"inputs":[],"name":"ProposedOwnable__onlyProposed_notProposedOwner","type":"error"},{"inputs":[],"name":"ProposedOwnable__ownershipDelayElapsed_delayNotElapsed","type":"error"},{"inputs":[],"name":"ProposedOwnable__proposeNewOwner_invalidProposal","type":"error"},{"inputs":[],"name":"ProposedOwnable__proposeNewOwner_noOwnershipChange","type":"error"},{"inputs":[],"name":"ProposedOwnable__renounceOwnership_invalidProposal","type":"error"},{"inputs":[],"name":"ProposedOwnable__renounceOwnership_noProposal","type":"error"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"_previous","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"_updated","type":"uint256"}],"name":"GasCapUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes","name":"data","type":"bytes"},{"indexed":false,"internalType":"address","name":"caller","type":"address"}],"name":"MessageProcessed","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes","name":"data","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"encodedData","type":"bytes"},{"indexed":false,"internalType":"address","name":"caller","type":"address"}],"name":"MessageSent","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"previous","type":"address"},{"indexed":false,"internalType":"address","name":"current","type":"address"}],"name":"MirrorConnectorUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint32","name":"domain","type":"uint32"},{"indexed":true,"internalType":"uint32","name":"mirrorDomain","type":"uint32"},{"indexed":false,"internalType":"address","name":"amb","type":"address"},{"indexed":false,"internalType":"address","name":"rootManager","type":"address"},{"indexed":false,"internalType":"address","name":"mirrorConnector","type":"address"}],"name":"NewConnector","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"proposedOwner","type":"address"}],"name":"OwnershipProposed","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":"address","name":"previous","type":"address"},{"indexed":true,"internalType":"address","name":"updated","type":"address"}],"name":"RefundAddressUpdated","type":"event"},{"inputs":[],"name":"AMB","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"DOMAIN","outputs":[{"internalType":"uint32","name":"","type":"uint32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"MIRROR_DOMAIN","outputs":[{"internalType":"uint32","name":"","type":"uint32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"MIRROR_WORMHOLE_ID","outputs":[{"internalType":"uint16","name":"","type":"uint16"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"ROOT_MANAGER","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"acceptProposedOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"delay","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"mirrorConnector","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"_data","type":"bytes"}],"name":"processMessage","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"name":"processedWhMessages","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"newlyProposed","type":"address"}],"name":"proposeNewOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"proposed","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"proposedTimestamp","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_gasLimit","type":"uint256"},{"internalType":"address","name":"_amb","type":"address"}],"name":"quoteEVMDeliveryPrice","outputs":[{"internalType":"uint256","name":"_cost","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"_payload","type":"bytes"},{"internalType":"bytes[]","name":"","type":"bytes[]"},{"internalType":"bytes32","name":"_sourceAddress","type":"bytes32"},{"internalType":"uint16","name":"_sourceChain","type":"uint16"},{"internalType":"bytes32","name":"_deliveryHash","type":"bytes32"}],"name":"receiveWormholeMessages","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"refundAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"renounced","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"_data","type":"bytes"},{"internalType":"bytes","name":"_encodedData","type":"bytes"}],"name":"sendMessage","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_gasCap","type":"uint256"}],"name":"setGasCap","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_mirrorConnector","type":"address"}],"name":"setMirrorConnector","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_updated","type":"address"}],"name":"setRefundAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_expected","type":"address"}],"name":"verifySender","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"stateMutability":"payable","type":"receive"}]

6101206040523480156200001257600080fd5b5060405162001a2038038062001a2083398101604081905262000035916200039b565b818181898989898984848484846200004d33620001b3565b8463ffffffff16600003620000985760405162461bcd60e51b815260206004820152600c60248201526b32b6b83a3c903237b6b0b4b760a11b60448201526064015b60405180910390fd5b6001600160a01b038216620000e45760405162461bcd60e51b815260206004820152601160248201527032b6b83a3c903937b7ba26b0b730b3b2b960791b60448201526064016200008f565b63ffffffff8086166080526001600160a01b0380851660a05283811660c05290851660e0528116156200011c576200011c8162000218565b604080516001600160a01b0385811682528481166020830152831681830152905163ffffffff86811692908816917f4f9c27c2fe3f84576ea469d367d044da53c45e951617e8389f2b5ed8db9d25f09181900360600190a3505050505050505050506200018f816200028160201b60201c565b5061ffff811661010052620001a433620002c2565b50505050505050505062000431565b600080546040516001600160a01b03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b039092166001600160a01b0319928316178155600255600180549091169055565b600354604080516001600160a01b03928316815291831660208301527fc77bec288fc88f168427f2f7da682eadb26cac89d8d591af6e443da98dff2bbc910160405180910390a1600380546001600160a01b0319166001600160a01b0392909216919091179055565b60045460408051918252602082018390527f877a02cb809da0364d23adca3cd50c451b53f279d3df632e1fc11eb66335bce5910160405180910390a1600455565b6005546001600160a01b03908116908216036200030d5760405162461bcd60e51b81526020600482015260086024820152670858da185b99d95960c21b60448201526064016200008f565b6005546040516001600160a01b038084169216907f57b5839c3435f5b2eb2d2e286fb44ca7303d01d9b25a5d9c05c489523474285990600090a3600580546001600160a01b0319166001600160a01b0392909216919091179055565b805163ffffffff811681146200037e57600080fd5b919050565b80516001600160a01b03811681146200037e57600080fd5b600080600080600080600060e0888a031215620003b757600080fd5b620003c28862000369565b9650620003d26020890162000369565b9550620003e26040890162000383565b9450620003f26060890162000383565b9350620004026080890162000383565b925060a0880151915060c088015161ffff811681146200042157600080fd5b8091505092959891949750929550565b60805160a05160c05160e0516101005161156b620004b560003960008181610255015281816105e501528181610abe01526110080152600081816101aa0152610cc9015260008181610375015281816105280152610ca20152600081816104a401528181610691015281816107320152610a5901526000610321015261156b6000f3fe60806040526004361061014f5760003560e01c80635f61e3ec116100b6578063c5b350df1161006f578063c5b350df14610420578063cc39428314610435578063d1851c9214610455578063d232c22014610473578063d69f9d6114610492578063db1b7659146104c657600080fd5b80635f61e3ec146103635780636a42b8f814610397578063715018a6146103ad5780637850b020146103c25780638da5cb5b146103e2578063b1f8100d1461040057600080fd5b806348e6fa231161010857806348e6fa23146102a95780634d93538b146102bc5780634ff746f6146102dc578063529dca32146102fc57806352a9674b1461030f5780635bd11efc1461034357600080fd5b80630cb61f6c1461015b578063141684161461019857806315b75bea146101e157806318c8170914610203578063194ea996146102435780633cf52ffb1461028a57600080fd5b3661015657005b600080fd5b34801561016757600080fd5b5060055461017b906001600160a01b031681565b6040516001600160a01b0390911681526020015b60405180910390f35b3480156101a457600080fd5b506101cc7f000000000000000000000000000000000000000000000000000000000000000081565b60405163ffffffff909116815260200161018f565b3480156101ed57600080fd5b506102016101fc3660046110a5565b6104e6565b005b34801561020f57600080fd5b5061023361021e3660046110c7565b60066020526000908152604090205460ff1681565b604051901515815260200161018f565b34801561024f57600080fd5b506102777f000000000000000000000000000000000000000000000000000000000000000081565b60405161ffff909116815260200161018f565b34801561029657600080fd5b506002545b60405190815260200161018f565b6102016102b7366004611197565b61051d565b3480156102c857600080fd5b5061029b6102d73660046111fb565b6105d2565b3480156102e857600080fd5b506102016102f7366004611227565b610686565b61020161030a366004611276565b61072c565b34801561031b57600080fd5b506101cc7f000000000000000000000000000000000000000000000000000000000000000081565b34801561034f57600080fd5b5061020161035e3660046110a5565b610770565b34801561036f57600080fd5b5061017b7f000000000000000000000000000000000000000000000000000000000000000081565b3480156103a357600080fd5b5062093a8061029b565b3480156103b957600080fd5b506102016107a4565b3480156103ce57600080fd5b506102016103dd3660046110c7565b610858565b3480156103ee57600080fd5b506000546001600160a01b031661017b565b34801561040c57600080fd5b5061020161041b3660046110a5565b61088c565b34801561042c57600080fd5b5061020161092a565b34801561044157600080fd5b5060035461017b906001600160a01b031681565b34801561046157600080fd5b506001546001600160a01b031661017b565b34801561047f57600080fd5b506000546001600160a01b031615610233565b34801561049e57600080fd5b5061017b7f000000000000000000000000000000000000000000000000000000000000000081565b3480156104d257600080fd5b506102336104e13660046110a5565b61099a565b6000546001600160a01b03163314610511576040516311a8a1bb60e31b815260040160405180910390fd5b61051a816109ab565b50565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146105895760405162461bcd60e51b815260206004820152600c60248201526b10b937b7ba26b0b730b3b2b960a11b60448201526064015b60405180910390fd5b6105938282610a50565b7fdcaa37a042a0087de79018c629bbd29cee82ca80bd9be394e1696bf9e93550778282336040516105c6939291906113c5565b60405180910390a15050565b6000816001600160a01b031663c23ee3c37f0000000000000000000000000000000000000000000000000000000000000000600061060f87610a8d565b6040516001600160e01b031960e086901b16815261ffff9093166004840152602483019190915260448201526064016040805180830381865afa15801561065a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061067e9190611403565b509392505050565b336001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016146106e75760405162461bcd60e51b81526004016105809060208082526004908201526310a0a6a160e11b604082015260600190565b6106f081610aa3565b7fb3abc57bfeebd2cac918901db582f71972a8e628bccf19f5ae3e3482b98a5ced8133604051610721929190611427565b60405180910390a150565b610757827f000000000000000000000000000000000000000000000000000000000000000083610abc565b61076961076384610bd6565b86610c19565b5050505050565b6000546001600160a01b0316331461079b576040516311a8a1bb60e31b815260040160405180910390fd5b61051a81610d7e565b6000546001600160a01b031633146107cf576040516311a8a1bb60e31b815260040160405180910390fd5b62093a80600254426107e19190611451565b116107ff576040516324e0285f60e21b815260040160405180910390fd5b60025460000361082257604051630e4b303f60e21b815260040160405180910390fd5b6001546001600160a01b03161561084c576040516323295ef960e01b815260040160405180910390fd5b6108566000610de7565b565b6000546001600160a01b03163314610883576040516311a8a1bb60e31b815260040160405180910390fd5b61051a81610e4c565b6000546001600160a01b031633146108b7576040516311a8a1bb60e31b815260040160405180910390fd5b6001546001600160a01b0382811691161480156108d5575060025415155b156108f3576040516311bc066560e11b815260040160405180910390fd5b6000546001600160a01b0380831691160361092157604051634a2fb73f60e11b815260040160405180910390fd5b61051a81610e8d565b6001546001600160a01b03163314610955576040516311a7f27160e11b815260040160405180910390fd5b62093a80600254426109679190611451565b11610985576040516324e0285f60e21b815260040160405180910390fd5b600154610856906001600160a01b0316610de7565b60006109a582610edb565b92915050565b6005546001600160a01b03908116908216036109f45760405162461bcd60e51b81526020600482015260086024820152670858da185b99d95960c21b6044820152606401610580565b6005546040516001600160a01b038084169216907f57b5839c3435f5b2eb2d2e286fb44ca7303d01d9b25a5d9c05c489523474285990600090a3600580546001600160a01b0319166001600160a01b0392909216919091179055565b600354610a89907f0000000000000000000000000000000000000000000000000000000000000000906001600160a01b03168484610ef4565b5050565b6000600454821115610a9f5760045491505b5090565b6040516316c2fdb560e21b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000061ffff168361ffff1614610b235760405162461bcd60e51b815260206004820152600d60248201526c10b9b7bab931b29031b430b4b760991b6044820152606401610580565b336001600160a01b03831614610b665760405162461bcd60e51b815260206004820152600860248201526710b932b630bcb2b960c11b6044820152606401610580565b60008181526006602052604090205460ff1615610bb95760405162461bcd60e51b8152602060048201526011602482015270185b1c9958591e481c1c9bd8d95cdcd959607a1b6044820152606401610580565b6000908152600660205260409020805460ff191660011790555050565b600060a082901c15610a9f5760405162461bcd60e51b815260206004820152600c60248201526b2165766d206164647265737360a01b6044820152606401610580565b610c2282610edb565b610c5d5760405162461bcd60e51b815260206004820152600c60248201526b10b61921b7b73732b1ba37b960a11b6044820152606401610580565b8051602014610c985760405162461bcd60e51b8152602060048201526007602482015266042d8cadccee8d60cb1b6044820152606401610580565b6001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016638e7d93fa7f0000000000000000000000000000000000000000000000000000000000000000610cf184611472565b6040516001600160e01b031960e085901b16815263ffffffff9290921660048301526024820152604401600060405180830381600087803b158015610d3557600080fd5b505af1158015610d49573d6000803e3d6000fd5b505050507fb3abc57bfeebd2cac918901db582f71972a8e628bccf19f5ae3e3482b98a5ced81336040516105c6929190611427565b600354604080516001600160a01b03928316815291831660208301527fc77bec288fc88f168427f2f7da682eadb26cac89d8d591af6e443da98dff2bbc910160405180910390a1600380546001600160a01b0319166001600160a01b0392909216919091179055565b600080546040516001600160a01b03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b039092166001600160a01b0319928316178155600255600180549091169055565b60045460408051918252602082018390527f877a02cb809da0364d23adca3cd50c451b53f279d3df632e1fc11eb66335bce5910160405180910390a1600455565b42600255600180546001600160a01b0319166001600160a01b0383169081179091556040517f6ab4d119f23076e8ad491bc65ce85f017fb0591dce08755ba8591059cc51737a90600090a250565b6003546000906001600160a01b038381169116146109a5565b8151602014610f345760405162461bcd60e51b815260206004820152600c60248201526b042c8c2e8c240d8cadccee8d60a31b6044820152606401610580565b8051602014610f7c5760405162461bcd60e51b8152602060048201526014602482015273042cadcc6dec8cac840c8c2e8c240d8cadccee8d60631b6044820152606401610580565b600081806020019051810190610f929190611499565b90506000610fa082876105d2565b9050348114610fde5760405162461bcd60e51b815260206004820152600a602482015269216d73672e76616c756560b01b6044820152606401610580565b6005546040516312d729bd60e21b81526001600160a01b0380891692634b5ca6f492859261103d927f0000000000000000000000000000000000000000000000000000000000000000928c928c926000928c92879216906004016114b2565b60206040518083038185885af115801561105b573d6000803e3d6000fd5b50505050506040513d601f19601f82011682018060405250810190611080919061150b565b50505050505050565b80356001600160a01b03811681146110a057600080fd5b919050565b6000602082840312156110b757600080fd5b6110c082611089565b9392505050565b6000602082840312156110d957600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561111f5761111f6110e0565b604052919050565b600082601f83011261113857600080fd5b813567ffffffffffffffff811115611152576111526110e0565b611165601f8201601f19166020016110f6565b81815284602083860101111561117a57600080fd5b816020850160208301376000918101602001919091529392505050565b600080604083850312156111aa57600080fd5b823567ffffffffffffffff808211156111c257600080fd5b6111ce86838701611127565b935060208501359150808211156111e457600080fd5b506111f185828601611127565b9150509250929050565b6000806040838503121561120e57600080fd5b8235915061121e60208401611089565b90509250929050565b60006020828403121561123957600080fd5b813567ffffffffffffffff81111561125057600080fd5b61125c84828501611127565b949350505050565b803561ffff811681146110a057600080fd5b600080600080600060a0868803121561128e57600080fd5b853567ffffffffffffffff808211156112a657600080fd5b6112b289838a01611127565b96506020915081880135818111156112c957600080fd5b8801601f81018a136112da57600080fd5b8035828111156112ec576112ec6110e0565b8060051b6112fb8582016110f6565b918252828101850191858101908d84111561131557600080fd5b86850192505b83831015611351578235868111156113335760008081fd5b6113418f8983890101611127565b835250918601919086019061131b565b809a50505050505050506040860135925061136e60608701611264565b949793965091946080013592915050565b6000815180845260005b818110156113a557602081850181015186830182015201611389565b506000602082860101526020601f19601f83011685010191505092915050565b6060815260006113d8606083018661137f565b82810360208401526113ea818661137f565b91505060018060a01b0383166040830152949350505050565b6000806040838503121561141657600080fd5b505080516020909101519092909150565b60408152600061143a604083018561137f565b905060018060a01b03831660208301529392505050565b818103818111156109a557634e487b7160e01b600052601160045260246000fd5b80516020808301519190811015611493576000198160200360031b1b821691505b50919050565b6000602082840312156114ab57600080fd5b5051919050565b600061ffff808a16835260018060a01b03808a16602085015260e060408501526114df60e085018a61137f565b925087606085015286608085015281861660a085015280851660c0850152505098975050505050505050565b60006020828403121561151d57600080fd5b815167ffffffffffffffff811681146110c057600080fdfea26469706673582212207fae5ae139ba9412dd3eb66ea44881835a9cf3d5dfc7e4643f136b945ae492a364736f6c6343000811003300000000000000000000000000000000000000000000000000000000006574680000000000000000000000000000000000000000000000000000000000626e6200000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d894911000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e1000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000493e00000000000000000000000000000000000000000000000000000000000000004

Deployed Bytecode

0x60806040526004361061014f5760003560e01c80635f61e3ec116100b6578063c5b350df1161006f578063c5b350df14610420578063cc39428314610435578063d1851c9214610455578063d232c22014610473578063d69f9d6114610492578063db1b7659146104c657600080fd5b80635f61e3ec146103635780636a42b8f814610397578063715018a6146103ad5780637850b020146103c25780638da5cb5b146103e2578063b1f8100d1461040057600080fd5b806348e6fa231161010857806348e6fa23146102a95780634d93538b146102bc5780634ff746f6146102dc578063529dca32146102fc57806352a9674b1461030f5780635bd11efc1461034357600080fd5b80630cb61f6c1461015b578063141684161461019857806315b75bea146101e157806318c8170914610203578063194ea996146102435780633cf52ffb1461028a57600080fd5b3661015657005b600080fd5b34801561016757600080fd5b5060055461017b906001600160a01b031681565b6040516001600160a01b0390911681526020015b60405180910390f35b3480156101a457600080fd5b506101cc7f0000000000000000000000000000000000000000000000000000000000626e6281565b60405163ffffffff909116815260200161018f565b3480156101ed57600080fd5b506102016101fc3660046110a5565b6104e6565b005b34801561020f57600080fd5b5061023361021e3660046110c7565b60066020526000908152604090205460ff1681565b604051901515815260200161018f565b34801561024f57600080fd5b506102777f000000000000000000000000000000000000000000000000000000000000000481565b60405161ffff909116815260200161018f565b34801561029657600080fd5b506002545b60405190815260200161018f565b6102016102b7366004611197565b61051d565b3480156102c857600080fd5b5061029b6102d73660046111fb565b6105d2565b3480156102e857600080fd5b506102016102f7366004611227565b610686565b61020161030a366004611276565b61072c565b34801561031b57600080fd5b506101cc7f000000000000000000000000000000000000000000000000000000000065746881565b34801561034f57600080fd5b5061020161035e3660046110a5565b610770565b34801561036f57600080fd5b5061017b7f000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e181565b3480156103a357600080fd5b5062093a8061029b565b3480156103b957600080fd5b506102016107a4565b3480156103ce57600080fd5b506102016103dd3660046110c7565b610858565b3480156103ee57600080fd5b506000546001600160a01b031661017b565b34801561040c57600080fd5b5061020161041b3660046110a5565b61088c565b34801561042c57600080fd5b5061020161092a565b34801561044157600080fd5b5060035461017b906001600160a01b031681565b34801561046157600080fd5b506001546001600160a01b031661017b565b34801561047f57600080fd5b506000546001600160a01b031615610233565b34801561049e57600080fd5b5061017b7f00000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d89491181565b3480156104d257600080fd5b506102336104e13660046110a5565b61099a565b6000546001600160a01b03163314610511576040516311a8a1bb60e31b815260040160405180910390fd5b61051a816109ab565b50565b336001600160a01b037f000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e116146105895760405162461bcd60e51b815260206004820152600c60248201526b10b937b7ba26b0b730b3b2b960a11b60448201526064015b60405180910390fd5b6105938282610a50565b7fdcaa37a042a0087de79018c629bbd29cee82ca80bd9be394e1696bf9e93550778282336040516105c6939291906113c5565b60405180910390a15050565b6000816001600160a01b031663c23ee3c37f0000000000000000000000000000000000000000000000000000000000000004600061060f87610a8d565b6040516001600160e01b031960e086901b16815261ffff9093166004840152602483019190915260448201526064016040805180830381865afa15801561065a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061067e9190611403565b509392505050565b336001600160a01b037f00000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d89491116146106e75760405162461bcd60e51b81526004016105809060208082526004908201526310a0a6a160e11b604082015260600190565b6106f081610aa3565b7fb3abc57bfeebd2cac918901db582f71972a8e628bccf19f5ae3e3482b98a5ced8133604051610721929190611427565b60405180910390a150565b610757827f00000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d89491183610abc565b61076961076384610bd6565b86610c19565b5050505050565b6000546001600160a01b0316331461079b576040516311a8a1bb60e31b815260040160405180910390fd5b61051a81610d7e565b6000546001600160a01b031633146107cf576040516311a8a1bb60e31b815260040160405180910390fd5b62093a80600254426107e19190611451565b116107ff576040516324e0285f60e21b815260040160405180910390fd5b60025460000361082257604051630e4b303f60e21b815260040160405180910390fd5b6001546001600160a01b03161561084c576040516323295ef960e01b815260040160405180910390fd5b6108566000610de7565b565b6000546001600160a01b03163314610883576040516311a8a1bb60e31b815260040160405180910390fd5b61051a81610e4c565b6000546001600160a01b031633146108b7576040516311a8a1bb60e31b815260040160405180910390fd5b6001546001600160a01b0382811691161480156108d5575060025415155b156108f3576040516311bc066560e11b815260040160405180910390fd5b6000546001600160a01b0380831691160361092157604051634a2fb73f60e11b815260040160405180910390fd5b61051a81610e8d565b6001546001600160a01b03163314610955576040516311a7f27160e11b815260040160405180910390fd5b62093a80600254426109679190611451565b11610985576040516324e0285f60e21b815260040160405180910390fd5b600154610856906001600160a01b0316610de7565b60006109a582610edb565b92915050565b6005546001600160a01b03908116908216036109f45760405162461bcd60e51b81526020600482015260086024820152670858da185b99d95960c21b6044820152606401610580565b6005546040516001600160a01b038084169216907f57b5839c3435f5b2eb2d2e286fb44ca7303d01d9b25a5d9c05c489523474285990600090a3600580546001600160a01b0319166001600160a01b0392909216919091179055565b600354610a89907f00000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d894911906001600160a01b03168484610ef4565b5050565b6000600454821115610a9f5760045491505b5090565b6040516316c2fdb560e21b815260040160405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000461ffff168361ffff1614610b235760405162461bcd60e51b815260206004820152600d60248201526c10b9b7bab931b29031b430b4b760991b6044820152606401610580565b336001600160a01b03831614610b665760405162461bcd60e51b815260206004820152600860248201526710b932b630bcb2b960c11b6044820152606401610580565b60008181526006602052604090205460ff1615610bb95760405162461bcd60e51b8152602060048201526011602482015270185b1c9958591e481c1c9bd8d95cdcd959607a1b6044820152606401610580565b6000908152600660205260409020805460ff191660011790555050565b600060a082901c15610a9f5760405162461bcd60e51b815260206004820152600c60248201526b2165766d206164647265737360a01b6044820152606401610580565b610c2282610edb565b610c5d5760405162461bcd60e51b815260206004820152600c60248201526b10b61921b7b73732b1ba37b960a11b6044820152606401610580565b8051602014610c985760405162461bcd60e51b8152602060048201526007602482015266042d8cadccee8d60cb1b6044820152606401610580565b6001600160a01b037f000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e116638e7d93fa7f0000000000000000000000000000000000000000000000000000000000626e62610cf184611472565b6040516001600160e01b031960e085901b16815263ffffffff9290921660048301526024820152604401600060405180830381600087803b158015610d3557600080fd5b505af1158015610d49573d6000803e3d6000fd5b505050507fb3abc57bfeebd2cac918901db582f71972a8e628bccf19f5ae3e3482b98a5ced81336040516105c6929190611427565b600354604080516001600160a01b03928316815291831660208301527fc77bec288fc88f168427f2f7da682eadb26cac89d8d591af6e443da98dff2bbc910160405180910390a1600380546001600160a01b0319166001600160a01b0392909216919091179055565b600080546040516001600160a01b03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b039092166001600160a01b0319928316178155600255600180549091169055565b60045460408051918252602082018390527f877a02cb809da0364d23adca3cd50c451b53f279d3df632e1fc11eb66335bce5910160405180910390a1600455565b42600255600180546001600160a01b0319166001600160a01b0383169081179091556040517f6ab4d119f23076e8ad491bc65ce85f017fb0591dce08755ba8591059cc51737a90600090a250565b6003546000906001600160a01b038381169116146109a5565b8151602014610f345760405162461bcd60e51b815260206004820152600c60248201526b042c8c2e8c240d8cadccee8d60a31b6044820152606401610580565b8051602014610f7c5760405162461bcd60e51b8152602060048201526014602482015273042cadcc6dec8cac840c8c2e8c240d8cadccee8d60631b6044820152606401610580565b600081806020019051810190610f929190611499565b90506000610fa082876105d2565b9050348114610fde5760405162461bcd60e51b815260206004820152600a602482015269216d73672e76616c756560b01b6044820152606401610580565b6005546040516312d729bd60e21b81526001600160a01b0380891692634b5ca6f492859261103d927f0000000000000000000000000000000000000000000000000000000000000004928c928c926000928c92879216906004016114b2565b60206040518083038185885af115801561105b573d6000803e3d6000fd5b50505050506040513d601f19601f82011682018060405250810190611080919061150b565b50505050505050565b80356001600160a01b03811681146110a057600080fd5b919050565b6000602082840312156110b757600080fd5b6110c082611089565b9392505050565b6000602082840312156110d957600080fd5b5035919050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561111f5761111f6110e0565b604052919050565b600082601f83011261113857600080fd5b813567ffffffffffffffff811115611152576111526110e0565b611165601f8201601f19166020016110f6565b81815284602083860101111561117a57600080fd5b816020850160208301376000918101602001919091529392505050565b600080604083850312156111aa57600080fd5b823567ffffffffffffffff808211156111c257600080fd5b6111ce86838701611127565b935060208501359150808211156111e457600080fd5b506111f185828601611127565b9150509250929050565b6000806040838503121561120e57600080fd5b8235915061121e60208401611089565b90509250929050565b60006020828403121561123957600080fd5b813567ffffffffffffffff81111561125057600080fd5b61125c84828501611127565b949350505050565b803561ffff811681146110a057600080fd5b600080600080600060a0868803121561128e57600080fd5b853567ffffffffffffffff808211156112a657600080fd5b6112b289838a01611127565b96506020915081880135818111156112c957600080fd5b8801601f81018a136112da57600080fd5b8035828111156112ec576112ec6110e0565b8060051b6112fb8582016110f6565b918252828101850191858101908d84111561131557600080fd5b86850192505b83831015611351578235868111156113335760008081fd5b6113418f8983890101611127565b835250918601919086019061131b565b809a50505050505050506040860135925061136e60608701611264565b949793965091946080013592915050565b6000815180845260005b818110156113a557602081850181015186830182015201611389565b506000602082860101526020601f19601f83011685010191505092915050565b6060815260006113d8606083018661137f565b82810360208401526113ea818661137f565b91505060018060a01b0383166040830152949350505050565b6000806040838503121561141657600080fd5b505080516020909101519092909150565b60408152600061143a604083018561137f565b905060018060a01b03831660208301529392505050565b818103818111156109a557634e487b7160e01b600052601160045260246000fd5b80516020808301519190811015611493576000198160200360031b1b821691505b50919050565b6000602082840312156114ab57600080fd5b5051919050565b600061ffff808a16835260018060a01b03808a16602085015260e060408501526114df60e085018a61137f565b925087606085015286608085015281861660a085015280851660c0850152505098975050505050505050565b60006020828403121561151d57600080fd5b815167ffffffffffffffff811681146110c057600080fdfea26469706673582212207fae5ae139ba9412dd3eb66ea44881835a9cf3d5dfc7e4643f136b945ae492a364736f6c63430008110033

Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)

00000000000000000000000000000000000000000000000000000000006574680000000000000000000000000000000000000000000000000000000000626e6200000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d894911000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e1000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000493e00000000000000000000000000000000000000000000000000000000000000004

-----Decoded View---------------
Arg [0] : _domain (uint32): 6648936
Arg [1] : _mirrorDomain (uint32): 6450786
Arg [2] : _amb (address): 0x27428DD2d3DD32A4D7f7C497eAaa23130d894911
Arg [3] : _rootManager (address): 0xd5d61E9dfb6680Cba8353988Ba0337802811C2e1
Arg [4] : _mirrorConnector (address): 0x0000000000000000000000000000000000000000
Arg [5] : _gasCap (uint256): 300000
Arg [6] : _mirrorWormholeChainId (uint16): 4

-----Encoded View---------------
7 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000657468
Arg [1] : 0000000000000000000000000000000000000000000000000000000000626e62
Arg [2] : 00000000000000000000000027428dd2d3dd32a4d7f7c497eaaa23130d894911
Arg [3] : 000000000000000000000000d5d61e9dfb6680cba8353988ba0337802811c2e1
Arg [4] : 0000000000000000000000000000000000000000000000000000000000000000
Arg [5] : 00000000000000000000000000000000000000000000000000000000000493e0
Arg [6] : 0000000000000000000000000000000000000000000000000000000000000004


Block Transaction Difficulty Gas Used Reward
View All Blocks Produced

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

Validator Index Block Amount
View All Withdrawals

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

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