Skip to main content
This guide covers how to configure the security and execution stack for your LayerZero OApp or OFT on Stellar.

Overview

Configuring a LayerZero application on Stellar involves these steps:
  1. Configure DVN — set verification parameters (required DVNs, optional DVNs, confirmations)
  2. Configure Executor — set execution parameters (max message size, executor address)
  3. Set Enforced Options — define minimum execution options per destination

DVN Configuration

DVNs (Decentralized Verifier Networks) verify crosschain messages. Configuration is done via the ULN-302 message library through the endpoint’s set_config function.

ULN Config Structure

The effective config must have at least one DVN — either required_dvns must be non-empty, or optional_dvn_threshold must be greater than 0.

Configure Send DVN

Set the DVN configuration for outbound messages:
Config type 2 = CONFIG_TYPE_SEND_ULN.

Configure Receive DVN

Set the DVN configuration for inbound messages:
Config type 3 = CONFIG_TYPE_RECEIVE_ULN.

OApp ULN Config

When setting per-OApp config, use OAppUlnConfig which includes flags to fall back to defaults:
Set a field’s use_default_* flag to true to inherit the network-wide default for that field, even if you customize other fields.
When a use_default_* flag is true, the corresponding config values must be zero or empty. For example, if use_default_confirmations is true, confirmations must be 0. If use_default_required_dvns is true, required_dvns must be empty. Violating this constraint will cause the transaction to fail.

Executor Configuration

The Executor delivers verified messages to the destination OApp. Configuration is also done via set_config:
Config type 1 = CONFIG_TYPE_EXECUTOR.
The config field in SetConfigParam is XDR-encoded bytes. Soroban contract types (OAppUlnConfig, OAppExecutorConfig) must be serialized to XDR before passing to set_config. Use the Stellar SDK’s toXDR() method or the stellar-xdr Rust crate to encode these structs.

Setting Enforced Options

Enforced options define the minimum execution parameters for outbound messages. They are combined with any caller-provided options:
The options field is Option<Bytes> — pass null to remove enforced options for a given eid/msg_type combination.
Always set enforced options for each destination. Without them, messages may fail due to insufficient gas on the destination chain. For SEND_AND_CALL (type 2), ensure the gas limit accounts for the compose execution.

Gas Options Example

When setting enforced options or passing extra_options in a send, you must specify the gas for lzReceive on the destination chain. The following examples use the standard LayerZero Type 3 encoding: The options format is: 0x0003 (Type 3 header) + 01 (executor worker ID) + 0011 (length = 17 bytes) + 01 (lzReceive option type) + gas as uint128.
Sending with empty extra_options and no enforced options will cause the send to fail with error #1114 at the message library level. Always include executor options specifying the gas for lzReceive on the destination.

Reading Configuration

Query the current configuration for your OApp:

Next Steps