Transport

TCP transport: connections, acceptors, connectors, and protocol framing.

ua::connection_protocol::Limits

struct

User-facing configuration limits offered during the Hello/ACK handshake.

These are the local side's proposed limits before negotiation. A single mMaxBufferSize is used symmetrically for both the send and receive buffer in the Hello/ACK exchange. All sizes are in bytes except mMaxChunkCount, which is a count.

Functions

bool operator==(const Limits &) const =default

Compares two limit sets field by field.

Returns: true when all fields are equal; false otherwise.

Public attributes

uint32_t mMaxBufferSize

Proposed send/receive buffer size, in bytes.

uint32_t mMaxMessageSize

Maximum assembled message size, in bytes.

uint32_t mMaxChunkCount

Maximum number of chunks per message.

Static attributes

constexpr uint32_t sDefaultBufferSize

Default send/receive buffer size, in bytes.

constexpr uint32_t sDefaultMaxMessageSize

Default maximum message size, in bytes.

constexpr uint32_t sDefaultMaxChunkCount

Default maximum number of chunks per message.

ua::connection_protocol::NegotiatedLimits

struct

Effective limits agreed by the Hello/ACK exchange and reported to the SecureChannel layer.

Unlike Limits, the values here are directional: they distinguish the constraints that apply to outgoing traffic from those that apply to incoming traffic, as resolved from the local proposal and the peer's reply. Size fields are in bytes; chunk-count fields are counts. A value of 0 in a maximum field means "no limit".

Functions

bool operator==(const NegotiatedLimits &) const =default

Compares two negotiated limit sets field by field.

Returns: true when all fields are equal; false otherwise.

Public attributes

uint32_t mSendBufferSize

Negotiated outgoing buffer size, in bytes.

uint32_t mReceiveBufferSize

Negotiated incoming buffer size, in bytes.

uint32_t mSendMaxMessageSize

Peer's limit on outgoing message size, in bytes (0 = no limit).

uint32_t mSendMaxChunkCount

Peer's limit on outgoing chunk count (0 = no limit).

uint32_t mRecvMaxMessageSize

Local limit on incoming message size, in bytes (0 = no limit).

uint32_t mRecvMaxChunkCount

Local limit on incoming chunk count (0 = no limit).

ua::TcpEndpoint

class

An immutable IPv4 or IPv6 transport endpoint: an IP address paired with a port.

Constructed through the static factory functions, which validate their inputs and throw on malformed addresses; the default-constructed value is the IPv4 address 0.0.0.0 on port 0. Instances are small, copyable value types with no shared ownership, and are safe to use from any thread.

Member types

IpVersion (enum)

IP protocol family of an endpoint's address.

  • V4 - 32-bit IPv4 address (4 bytes).
  • V6 - 128-bit IPv6 address (16 bytes).

Static functions

TcpEndpoint v4(std::span< const std::uint8_t > addr, std::uint16_t port)

Builds an IPv4 endpoint from raw address bytes.

  • addr (std::span< const std::uint8_t >) - Exactly 4 bytes in network (big-endian) order; copied into the endpoint.
  • port (std::uint16_t) - TCP port number in host byte order.

Returns: The constructed IPv4 endpoint.

TcpEndpoint v6(std::span< const std::uint8_t > addr, std::uint16_t port)

Builds an IPv6 endpoint from raw address bytes.

  • addr (std::span< const std::uint8_t >) - Exactly 16 bytes in network (big-endian) order; copied into the endpoint.
  • port (std::uint16_t) - TCP port number in host byte order.

Returns: The constructed IPv6 endpoint.

TcpEndpoint from_bytes(std::span< const std::uint8_t > addr, std::uint16_t port)

Builds an endpoint from raw address bytes, inferring the IP version from the length.

  • addr (std::span< const std::uint8_t >) - 4 bytes (IPv4) or 16 bytes (IPv6) in network (big-endian) order.
  • port (std::uint16_t) - TCP port number in host byte order.

Returns: The constructed endpoint.

TcpEndpoint from_string(std::string_view address, std::uint16_t port)

Builds an endpoint by parsing a textual IP address and an explicit port.

  • address (std::string_view) - Numeric IPv4 (e.g. "127.0.0.1") or IPv6 (e.g. "::1") address; not a hostname.
  • port (std::uint16_t) - TCP port number in host byte order.

Returns: The constructed endpoint, with version inferred from address.

TcpEndpoint from_string(std::string_view endpoint)

Builds an endpoint by parsing a combined "address:port" string.

  • endpoint (std::string_view) - Combined address and port; the address part must be a numeric IP literal, not a hostname.

Returns: The constructed endpoint.

Functions

TcpEndpoint()=default

Constructs the unspecified endpoint 0.0.0.0:0 (IPv4).

IpVersion version() const

Returns the IP version of this endpoint's address.

Returns: The IP version of this endpoint's address.

std::uint16_t port() const

Returns the TCP port number in host byte order.

Returns: The TCP port number in host byte order.

std::span< const std::uint8_t > address() const

Returns the address bytes in network (big-endian) order.

Returns: A non-owning view over the stored address bytes.

ua::TcpTransportAcceptor

class

A TCP listening socket that accepts inbound transport connections.

Binds a tcp::endpoint and runs a continuous async_accept loop on the executor supplied at construction; each accepted socket is wrapped in a TcpTransportConnection and handed to the new-connection callback. Construct only via create - the instance is shared-owned (enable_shared_from_this) and keeps itself alive across pending accepts. The type is neither copyable nor movable.

Member types

std::function< void(StatusCode, string_view, shared_ptr< TcpTransportConnection >)> NewConnectionCallback

Invoked for each inbound connection accepted by the listening socket.

Static functions

shared_ptr< TcpTransportAcceptor > create(boost::asio::any_io_executor executor, asio::ip::tcp::endpoint ipEndpoint, NewConnectionCallback newConnectionCallback, Logger logger={}, size_t writeQueueDepthCap=4096)

Creates a listening acceptor bound to ipEndpoint and starts accepting.

  • executor (boost::asio::any_io_executor) - Executor on which the accept loop runs and callbacks are invoked.
  • ipEndpoint (asio::ip::tcp::endpoint) - Local address and port to bind and listen on; port 0 selects an ephemeral port.
  • newConnectionCallback (NewConnectionCallback) - Invoked for each inbound connection (and on accept failure); see NewConnectionCallback.
  • logger (Logger) - Optional logger; a default-constructed logger discards output.
  • writeQueueDepthCap (size_t) - Pending-write queue cap applied to each accepted connection (see TcpTransportConnection::create).

Returns: A shared-owned acceptor that keeps itself alive across pending accepts.

Functions

~TcpTransportAcceptor()=default
asio::ip::tcp::endpoint get_local_endpoint() const

Returns the local endpoint (address and port) the acceptor is bound to.

Returns: The local endpoint (address and port) the acceptor is bound to.

void close_async(std::function< void(VoidResult)> callback={})

Closes the acceptor and stops accepting new connections.

  • callback (std::function< void(VoidResult)>) - Receives a VoidResult once the close completes; pass an empty callback for fire-and-forget close. This overload never throws.

ua::TcpTransportConnection

class

A TransportConnection over a connected Boost.Asio TCP socket.

Wraps an accepted or connected asio::ip::tcp::socket and adapts it to the SDK byte-stream transport contract: registered completion callbacks plus asynchronous reads and writes driven by the socket's executor. Instances are always heap-allocated and reference-counted; construct via create and hold the returned shared_ptr. Reads and writes run on the socket's executor, while their completion callbacks (registered via register_read_callback / register_write_callback) are invoked on the worker thread that ran the operation - do not block them.

Public methods are safe to call from any thread; mutable state is guarded by an internal mutex and (for close) the socket's executor. The object keeps itself alive across in-flight async operations through shared_from_this.

TransportConnection

Static functions

shared_ptr< TcpTransportConnection > create(asio::ip::tcp::socket &&socket, Logger logger={}, size_t writeQueueDepthCap=4096)

Creates a reference-counted connection that adopts socket.

  • socket (asio::ip::tcp::socket &&) - Connected TCP socket; moved into and owned by the connection.
  • logger (Logger) - Logger used for transport diagnostics; a default-constructed logger disables logging.
  • writeQueueDepthCap (size_t) - Maximum number of buffers allowed to wait in the pending-write queue before async_write fails closed (BadTcpNotEnoughResources). Bounds memory against a peer that stops draining the socket. Clamped to >= 1.

Returns: A shared_ptr owning the new connection.

Functions

~TcpTransportConnection()

Destroys the connection, closing the underlying socket if still open.

void register_error_callback(ErrorCallback callback) override

Registers the callback invoked on a transport-level socket error.

  • callback (ErrorCallback) - Receives the failing StatusCode and a human-readable description.
void register_read_callback(ReadCompleteCallback callback) override

Registers the callback invoked when an async_read completes.

  • callback (ReadCompleteCallback) - Receives the StatusCode, a description, and ownership of the filled buffer. Runs on the worker thread that completed the read; do not block it. Replaces any previously registered read callback.
void register_write_callback(WriteCompleteCallback callback) override

Registers the callback invoked when a queued async_write completes.

  • callback (WriteCompleteCallback) - Receives the StatusCode and a description. Runs on the worker thread that completed the write; do not block it. Replaces any previously registered write callback.
void async_read(std::vector< byte > &&buffer, size_t offset=0) override

Starts an asynchronous read that fills buffer from offset to its end.

  • buffer (std::vector< byte > &&) - Destination buffer; moved in and handed back through the read callback on completion.
  • offset (size_t) - Byte offset at which to begin writing into buffer.
size_t bytes_available_to_read() const override

Returns the number of bytes available to read without blocking.

Returns: Count of bytes currently readable from the socket's receive buffer.

StatusCode read(std::vector< byte > &buffer, size_t offset=0) override

Reads synchronously into buffer from offset to its end, blocking until complete.

  • buffer (std::vector< byte > &) - Destination buffer; the region from offset onward is overwritten with received bytes.
  • offset (size_t) - Byte offset at which to begin writing into buffer.

Returns: Status::Good on success, or Status::BadInternalError if the read fails or completes short.

void async_write(std::vector< byte > &&buffer) override

Queues buffer for asynchronous transmission.

  • buffer (std::vector< byte > &&) - Bytes to transmit; moved in and owned until the write completes.
void close_async(std::function< void(VoidResult)> callback={}) override

Closes the socket and invokes callback once any cancellation handlers queued by the close have run.

  • callback (std::function< void(VoidResult)>) - Invoked with a successful VoidResult once the close has drained. May be empty for fire-and-forget close. This overload never throws.
asio::ip::tcp::endpoint get_local_endpoint() const override

Returns the local TCP endpoint of the connection.

Returns: The local endpoint captured at construction, or a default-constructed endpoint if it could not be determined.

asio::ip::tcp::endpoint get_remote_endpoint() const

Returns the remote (peer) TCP endpoint of the connection.

Returns: The remote endpoint captured at construction, or a default-constructed endpoint if it could not be determined.

ua::TcpTransportConnector

class

Client-side TCP connector that asynchronously establishes one outbound connection.

Opens a socket to one endpoint or an ordered sequence of resolved endpoints; on success it delivers a ready TcpTransportConnection to the ConnectedCallback supplied at creation, and on aggregate failure it delivers the StatusCode and a diagnostic message instead. Instances are created via create and held through shared_ptr; the connector keeps itself alive across the in-flight connect. All work runs on the executor passed to create, and the completion callback is invoked on one of that executor's worker threads - do not block it.

Member types

std::function< void(StatusCode, string_view, shared_ptr< TcpTransportConnection >)> ConnectedCallback

Callback invoked once with the outcome of the connect attempt.

Static functions

shared_ptr< TcpTransportConnector > create(boost::asio::any_io_executor executor, asio::ip::tcp::endpoint ipEndpoint, ConnectedCallback connectedCallback, Logger logger={}, size_t writeQueueDepthCap=4096)

Creates a connector and begins connecting to ipEndpoint asynchronously.

  • executor (boost::asio::any_io_executor) - Executor on which the connect and its completion handler run.
  • ipEndpoint (asio::ip::tcp::endpoint) - Resolved TCP endpoint to connect to.
  • connectedCallback (ConnectedCallback) - Receives the connect outcome exactly once; must not be empty.
  • logger (Logger) - Logger for diagnostics; a disabled logger by default.
  • writeQueueDepthCap (size_t) - Pending-write queue cap applied to the established connection (see TcpTransportConnection::create). Bounds memory if the peer stops draining the socket - applies to outbound connections just as the acceptor's cap applies to inbound ones.

Returns: A shared_ptr to the new connector with the connect already in flight.

shared_ptr< TcpTransportConnector > create(boost::asio::any_io_executor executor, std::vector< asio::ip::tcp::endpoint > ipEndpoints, ConnectedCallback connectedCallback, Logger logger={}, size_t writeQueueDepthCap=4096)

Creates a connector and tries each resolved endpoint until one connects or all fail.

  • executor (boost::asio::any_io_executor) - Executor on which the connect attempts and completion handler run.
  • ipEndpoints (std::vector< asio::ip::tcp::endpoint >) - Ordered resolved TCP endpoints; must not be empty.
  • connectedCallback (ConnectedCallback) - Receives the aggregate connect outcome exactly once; must not be empty.
  • logger (Logger) - Logger for diagnostics; a disabled logger by default.
  • writeQueueDepthCap (size_t) - Pending-write queue cap applied to the established connection.

Returns: A shared_ptr to the new connector with the connect sequence already in flight.

Functions

~TcpTransportConnector()=default
void close_async(std::function< void(VoidResult)> callback={})

Cancels an in-flight connect by closing the socket and reports when teardown has completed.

ua::transport::BindAddress

struct

A local address a transport binds to in order to accept connections.

Pairs the transport profile with the profile-specific address string the transport listens on (for the default UA-TCP profile, an opc.tcp:// endpoint URL). A value type with no ownership or threading semantics.

Public attributes

TransportProfileId mTransportProfileId

Transport profile the address is interpreted under; selects how mAddress is parsed.

std::string mAddress

Profile-specific listen address (e.g. an opc.tcp:// URL for the UA-TCP profile).

ua::transport::EndpointUrl

class

An OPC UA endpoint URL (e.g.

opc.tcp://host:4840/path).

A thin value wrapper around the URL string that offers a minimal, transport-agnostic format check. It does not parse or validate the URL against any specific transport's grammar.

Functions

EndpointUrl()=default

Constructs an empty endpoint URL.

EndpointUrl(std::string url)

Constructs an endpoint URL wrapping the given string.

  • url (std::string) - The endpoint URL; taken by value and moved into storage. Not validated.
const std::string & str() const

Returns the wrapped URL string.

Returns: Reference to the URL, valid for the lifetime of this object.

bool has_basic_format() const

Reports whether the URL has a plausible scheme-bearing shape.

Returns: true if the URL is non-empty and contains ://; otherwise false.

ua::TransportConnection

class

A bidirectional byte-stream connection to a single peer.

Models one established transport-layer link (a connected TCP socket in the reference implementation) as the framing layer above it sees it: a sink for outbound bytes and a source for inbound bytes. Completion of asynchronous reads and writes is delivered through callbacks registered up front rather than per operation, so the framing layer registers its handlers once and then drives async_read / async_write against them.

Implementations are internally synchronized and may be used from any thread; registered callbacks run on an unspecified transport worker thread and must not block it. Ownership is shared - the connection typically outlives the call that issued an asynchronous operation, so completion handlers capture a weak reference and become no-ops once the connection is gone.

Member types

std::function< void(StatusCode, string_view)> ErrorCallback

Callback receiving an out-of-band socket error: status code and a human-readable description.

std::function< void(StatusCode, string_view, std::vector< byte > &&)> ReadCompleteCallback

Callback receiving the result of an async_read: status code, a description (set on failure), and the buffer handed to async_read moved back to the caller filled with the bytes read.

std::function< void(StatusCode, string_view)> WriteCompleteCallback

Callback receiving the result of an async_write: status code and a description (set on failure).

Functions

~TransportConnection()
void register_error_callback(ErrorCallback callback)=0

Registers the handler invoked when an out-of-band socket error is observed, replacing any previously registered handler.

  • callback (ErrorCallback) - Receives the error status and a description. Runs on a transport worker thread; must not block.
void register_read_callback(ReadCompleteCallback callback)=0

Registers the handler invoked when an async_read completes, replacing any previously registered handler.

  • callback (ReadCompleteCallback) - Receives Good and the filled buffer on success, or a Bad* status and description on failure. Runs on a transport worker thread; must not block.
void register_write_callback(WriteCompleteCallback callback)=0

Registers the handler invoked when an async_write completes, replacing any previously registered handler.

  • callback (WriteCompleteCallback) - Receives Good on success, or a Bad* status and description on failure. Runs on a transport worker thread; must not block.
asio::ip::tcp::endpoint get_local_endpoint() const =0

Returns the local endpoint (address and port) of this connection.

Returns: The local endpoint (address and port) of this connection.

void async_read(std::vector< byte > &&buffer, size_t offset=0)=0

Starts an asynchronous read that fills buffer from offset to its end.

  • buffer (std::vector< byte > &&) - Storage to fill, moved into the connection; the region [offset, size()) is the read target.
  • offset (size_t) - Index at which to begin writing read bytes; bytes before it are left untouched. Defaults to 0.
size_t bytes_available_to_read() const =0

Returns the number of bytes available to read immediately without blocking.

Returns: The number of bytes available to read immediately without blocking.

StatusCode read(std::vector< byte > &buffer, size_t offset=0)=0

Reads synchronously into buffer from offset to its end, blocking until the bytes arrive.

  • buffer (std::vector< byte > &) - Storage to fill; the region [offset, size()) is the read target.
  • offset (size_t) - Index at which to begin writing read bytes. Defaults to 0.

Returns: Good once the region is filled, or a Bad* status on error.

void async_write(std::vector< byte > &&buffer)=0

Queues buffer to be written and starts the write if the connection is idle.

  • buffer (std::vector< byte > &&) - Bytes to write, moved into the connection.
void close_async(std::function< void(VoidResult)> callback={})=0

Closes the connection and invokes callback once any cancellation handlers queued by the close have drained.

  • callback (std::function< void(VoidResult)>) - Receives a VoidResult once the close has drained. Pass an empty callback for fire-and-forget close (typical for inline error-recovery paths). Defaults to empty.

Was this page helpful?