Skip to main content

Overview

The TokenMessenger contract serves as the primary interface for users to burn tokens on the source chain and mint them on the destination chain. It integrates with both the MessageTransmitter for cross-chain messaging and the TokenMinter for token minting and burning operations.

State Variables

localMessageTransmitter
IMessageTransmitter
required
Local Message Transmitter responsible for sending and receiving messages to/from remote domains. This is an immutable reference set during contract deployment.
messageBodyVersion
uint32
required
Version of message body format. This immutable value defines the structure of burn messages.
localMinter
ITokenMinter
required
Minter responsible for minting and burning tokens on the local domain.
remoteTokenMessengers
mapping(uint32 => bytes32)
required
Mapping of domain to valid TokenMessenger addresses on remote domains.

Functions

depositForBurn

Deposits and burns tokens from sender to be minted on the destination domain.
function depositForBurn(
    uint256 amount,
    uint32 destinationDomain,
    bytes32 mintRecipient,
    address burnToken
) external returns (uint64 _nonce)
amount
uint256
required
Amount of tokens to burn. Must be greater than 0.
destinationDomain
uint32
required
Destination domain where tokens will be minted
mintRecipient
bytes32
required
Address of mint recipient on destination domain as bytes32. Must be nonzero.
burnToken
address
required
Address of contract to burn deposited tokens on local domain
Returns: uint64 - Unique nonce reserved by the message Behavior:
  • Transfers tokens from sender to the TokenMinter contract
  • Burns the tokens via the TokenMinter
  • Formats a burn message with token and recipient details
  • Sends the message via MessageTransmitter
  • Emits a DepositForBurn event
  • Any address can call receiveMessage() on the destination domain
Reverts if:
  • Amount is 0
  • Mint recipient is bytes32(0)
  • Given burnToken is not supported
  • Given destinationDomain has no TokenMessenger registered
  • transferFrom() fails (e.g., insufficient balance or allowance)
  • burn() fails
  • MessageTransmitter returns false or reverts

depositForBurnWithCaller

Deposits and burns tokens from sender to be minted on the destination domain. The mint on the destination domain must be called by the specified destinationCaller.
function depositForBurnWithCaller(
    uint256 amount,
    uint32 destinationDomain,
    bytes32 mintRecipient,
    address burnToken,
    bytes32 destinationCaller
) external returns (uint64 nonce)
amount
uint256
required
Amount of tokens to burn
destinationDomain
uint32
required
Destination domain
mintRecipient
bytes32
required
Address of mint recipient on destination domain
burnToken
address
required
Address of contract to burn deposited tokens on local domain
destinationCaller
bytes32
required
Caller on the destination domain, as bytes32. Must be nonzero.
Returns: uint64 - Unique nonce reserved by message
If the destinationCaller does not represent a valid address as bytes32, it will not be possible to broadcast the message on the destination domain. This is an advanced feature - the standard depositForBurn() should be preferred for most use cases.

handleReceiveMessage

Handles an incoming message received by the local MessageTransmitter. For a burn message, mints the associated token to the requested recipient on the local domain.
function handleReceiveMessage(
    uint32 remoteDomain,
    bytes32 sender,
    bytes calldata messageBody
) external returns (bool)
remoteDomain
uint32
required
The domain where the message originated from
sender
bytes32
required
The sender of the message (remote TokenMessenger)
messageBody
bytes
required
The message body bytes containing burn message details
Returns: bool - true if successful Validation:
  • Validates the local sender is the local MessageTransmitter
  • Validates the remote sender is a registered remote TokenMessenger for remoteDomain
  • Validates burn message format
  • Validates message body version
Behavior:
  • Extracts mint recipient, burn token, and amount from message body
  • Calls the TokenMinter to mint tokens to the recipient
  • Emits a MintAndWithdraw event

replaceDepositForBurn

Replaces a BurnMessage to change the mint recipient and/or destination caller. Allows the sender of a previous BurnMessage to send a new message to replace the original.
function replaceDepositForBurn(
    bytes calldata originalMessage,
    bytes calldata originalAttestation,
    bytes32 newDestinationCaller,
    bytes32 newMintRecipient
) external
originalMessage
bytes
required
Original message bytes to replace
originalAttestation
bytes
required
Original attestation bytes. Must be a valid attestation of originalMessage.
newDestinationCaller
bytes32
required
The new destination caller, which may be the same as the original destination caller, a new destination caller, or an empty destination caller (bytes32(0), indicating that any destination caller is valid)
newMintRecipient
bytes32
required
The new mint recipient, which may be the same as the original mint recipient or different. Must be nonzero.
Behavior:
  • Validates message format and attestation
  • Verifies msg.sender matches the sender of the original message
  • Reuses the original message’s amount and burn token
  • Does not require a new deposit
  • Emits a new DepositForBurn event
The new message will reuse the original message’s nonce. For a given nonce, all replacement message(s) and the original message are valid to broadcast on the destination domain, until the first message at the nonce confirms, at which point all others are invalidated.

addRemoteTokenMessenger

Adds a TokenMessenger for a remote domain. Only callable by the contract owner.
function addRemoteTokenMessenger(
    uint32 domain,
    bytes32 tokenMessenger
) external
domain
uint32
required
Domain of remote TokenMessenger
tokenMessenger
bytes32
required
Address of remote TokenMessenger as bytes32. Must be nonzero.
Reverts if:
  • tokenMessenger is bytes32(0)
  • A TokenMessenger is already set for the domain

removeRemoteTokenMessenger

Removes the TokenMessenger for a remote domain. Only callable by the contract owner.
function removeRemoteTokenMessenger(uint32 domain) external
domain
uint32
required
Domain of remote TokenMessenger to remove
Reverts if:
  • No TokenMessenger is set for the given remote domain

addLocalMinter

Adds a minter for the local domain. Only callable by the contract owner.
function addLocalMinter(address newLocalMinter) external
newLocalMinter
address
required
The address of the minter on the local domain. Must be nonzero.
Reverts if:
  • newLocalMinter is address(0)
  • A local minter is already set

removeLocalMinter

Removes the minter for the local domain. Only callable by the contract owner.
function removeLocalMinter() external
Reverts if:
  • No local minter is set

Events

DepositForBurn

Emitted when a DepositForBurn message is sent.
event DepositForBurn(
    uint64 indexed nonce,
    address indexed burnToken,
    uint256 amount,
    address indexed depositor,
    bytes32 mintRecipient,
    uint32 destinationDomain,
    bytes32 destinationTokenMessenger,
    bytes32 destinationCaller
)
nonce
uint64
Unique nonce reserved by message
burnToken
address
Address of token burnt on source domain
amount
uint256
Deposit amount
depositor
address
Address where deposit is transferred from
mintRecipient
bytes32
Address receiving minted tokens on destination domain as bytes32
destinationDomain
uint32
Destination domain
destinationTokenMessenger
bytes32
Address of TokenMessenger on destination domain as bytes32
destinationCaller
bytes32
Authorized caller as bytes32 of receiveMessage() on destination domain. If equal to bytes32(0), any address can call receiveMessage().

MintAndWithdraw

Emitted when tokens are minted on the destination domain.
event MintAndWithdraw(
    address indexed mintRecipient,
    uint256 amount,
    address indexed mintToken
)
mintRecipient
address
Recipient address of minted tokens
amount
uint256
Amount of minted tokens
mintToken
address
Contract address of minted token

RemoteTokenMessengerAdded

Emitted when a remote TokenMessenger is added.
event RemoteTokenMessengerAdded(uint32 domain, bytes32 tokenMessenger)

RemoteTokenMessengerRemoved

Emitted when a remote TokenMessenger is removed.
event RemoteTokenMessengerRemoved(uint32 domain, bytes32 tokenMessenger)

LocalMinterAdded

Emitted when the local minter is added.
event LocalMinterAdded(address localMinter)

LocalMinterRemoved

Emitted when the local minter is removed.
event LocalMinterRemoved(address localMinter)

Integration

The TokenMessenger integrates with two key contracts:

MessageTransmitter Integration

  • Uses sendMessage() or sendMessageWithCaller() to send burn messages cross-chain
  • Uses replaceMessage() to replace existing burn messages
  • Implements IMessageHandler interface to receive messages via handleReceiveMessage()

TokenMinter Integration

  • Calls burn() to burn tokens on the source chain
  • Calls mint() to mint tokens on the destination chain
  • Manages the relationship with the local TokenMinter instance

Build docs developers (and LLMs) love