aeron-io/aeron · error · IllegalArgumentException

control has port=0 for subscription: channel=

Error message

control has port=0 for subscription: channel={channel}

What it means

The Java Aeron driver rejects a subscription whose channel URI specifies an explicit control address with port 0. For subscriptions, the explicit control endpoint must have a concrete (non-zero) port so the driver knows where to receive control/setup traffic. This static validation runs in DriverConductor when a network publication or subscription is being added.

Solutions

  1. Set an explicit non-zero control-port in the channel URI (e.g. control-mode=manual|control=localhost:40456).
  2. Remove the explicit control address if you do not need MDC and rely on the default control channel instead.
  3. For publications-only, leave port 0 (dynamic control port) but never on the subscription side.
  4. Add a config validation step that parses the URI and checks control-port != 0 before calling addSubscription().

Example fix

// before
String uri = "aeron:udp?control=224.0.1.1:0|control-mode=manual";
aeron.addSubscription(uri, 1001);
// after
String uri = "aeron:udp?interface=0.0.0.0:0|control=224.0.1.1:40456|control-mode=manual";
aeron.addSubscription(uri, 1001);
Defensive patterns

Strategy: validation

Validate before calling

ChannelUri uri = ChannelUri.parse(channel);
String control = uri.get("control");
if (control != null && control.endsWith(":0")) throw new IllegalArgumentException("control must not use port 0 for subscriptions");

Type guard

boolean hasValidControlPort(ChannelUri uri) {
  String c = uri.get("control");
  return c == null || !c.endsWith(":0");
}

Try / catch

try { aeron.addSubscription(uri, streamId); }
catch (IllegalArgumentException e) { if (e.getMessage().contains("port=0 for subscription")) { /* fix URI: set explicit control-port */ } else throw e; }

Prevention

When it happens

Trigger: Calling Aeron.addSubscription() (or a destination variant) with a channel URI like "aeron:udp?control=hostname|control-port=0" (an explicit control-mode=manual/manual multicast or MDC control address with port 0).

Common situations: Copy-pasting a publication URI (where port 0 can be legal for an ephemeral control port) into a subscription; templated configs where the control-port placeholder was never filled in; MDC setup where the control endpoint was confused with the data endpoint.

Understand the failure class

Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.

Related errors


AI-assisted analysis of aeron-io/aeron@6d60124e15 (2026-09-12). Data as JSON: /api/errors/9bcc0205ffebf81f. Report an issue: GitHub.

Appendix: source

Thrown at aeron-driver/src/main/java/io/aeron/driver/DriverConductor.java:2356

                "'control-mode=dynamic' requires that 'control' parameter is set, channel=" +
                    udpChannel.originalUriString());
        }

        if (udpChannel.hasExplicitControl() && !udpChannel.hasExplicitEndpoint() &&
            ControlMode.NONE == udpChannel.controlMode())
        {
            throw new IllegalArgumentException(
                "'control' parameter requires that either 'endpoint' or 'control-mode' is specified, channel=" +
                    udpChannel.originalUriString());
        }
    }

    private static void validateControlForSubscription(final UdpChannel udpChannel)
    {
        if (udpChannel.hasExplicitControl() &&
            0 == udpChannel.localControl().getPort())
        {
            throw new IllegalArgumentException(MDC_CONTROL_PARAM_NAME + " has port=0 for subscription: channel=" +
                udpChannel.originalUriString());
        }
    }

    private static void validateTimestampConfiguration(final UdpChannel udpChannel)
    {
        if (null != udpChannel.channelUri().get(MEDIA_RCV_TIMESTAMP_OFFSET_PARAM_NAME))
        {
            throw new InvalidChannelException(
                "Media timestamps '" + MEDIA_RCV_TIMESTAMP_OFFSET_PARAM_NAME +
                    "' are not supported in the Java driver: channel=" + udpChannel.originalUriString());
        }
    }

    private static void validateDestinationUri(final ChannelUri uri, final String destinationUri)
    {
        if (SPY_QUALIFIER.equals(uri.prefix()))
        {

View on GitHub (pinned to 6d60124e15)