Skip to navigation

hololink::module::Adapter

View as Markdown

Process-wide entry point to the module system.

Discovers devices on the network, resolves each to the module that drives it, and hands the application the Module from which it resolves that device’s versioned service interfaces. One singleton instance serves the process.

Use Adapter::get_adapter to get a reference to this singleton object.

#include <hololink/module/adapter.hpp>

Methods

set_log_level

void hololink::module::Adapter::set_log_level(
LogLevel level
)

Set the threshold for log messages from the host and every loaded module.

Overrides the level chosen at startup from the HOLOLINK_LOG_LEVEL / HOLOSCAN_LOG_LEVEL environment variables (default Info). Takes effect immediately and may be called from any thread.

Parameters

level
LogLevel

Messages below this level are discarded.

host_publisher

std::shared_ptr<Publisher> hololink::module::Adapter::host_publisher() const

The Publisher through which the host offers services.

Services which are instantiated by the host application include

  • ReactorV1 provides a runtime environment for callback execution execution
  • LoggingInterfaceV1 allows loaded modules to forward their log messages to the application
  • Module provides get_service access for these application level services

Returns: The host publisher.

enumerate

void hololink::module::Adapter::enumerate(
const uint8_t *raw_packet = nullptr,
size_t raw_packet_len = 0
)

Application specific device announcement to the discovery pipeline.

Ordinarily, applications use Adapter::register_* in order to enumerate devices; as those devices are discovered (e.g. via received bootp messages), EnumerationMetadata is built and used to load up the driver module. If your application enumerates a device in a different way, you can create your own EnumerationMetadata instance and pass it in to this method in order to trigger loading of the appropriate driver module. A call here results in execution of the ordinary enumeration callbacks registered by the application. In other words, you can supply your own EnumerationMetadata if the ordinary bootp-based process doesn’t work.

Note that applications do not normally call this - devices are announced as their bootp packets arrive; this API is appropriate for special devices and test fixtures.

Throws: std::runtime_error if metadata carries no “fpga_uuid”, or if the claiming module rejects it for any reason other than declining the device.

Parameters

metadata
EnumerationMetadata

The device to announce.

raw_packet
const uint8_t *Defaults to nullptr

The bootp packet metadata was decoded from, handed on to the claiming module: one whose devices carry vendor-specific bytes needs it to complete the metadata. Omit it, or pass in nullptr, when the announcement did not come from a packet.

raw_packet_len
size_tDefaults to 0

Length of raw_packet, in bytes.

wait_for_channel

EnumerationMetadata hololink::module::Adapter::wait_for_channel(
const std::string &peer_ip,
std::chrono::milliseconds timeout
)

Wait for a device to announce itself, and return its enumeration metadata.

Returns: The device’s metadata (possibly supplemented by its driver module).

Throws: std::runtime_error if the timeout elapses first.

Parameters

peer_ip
const std::string &

Address of the device to wait for.

timeout
std::chrono::milliseconds

How long to wait before giving up.

register_ip

EnumerationCallbackHandle hololink::module::Adapter::register_ip(
std::string peer_ip,
std::function<void(const EnumerationMetadata &)> callback
)

Subscribe to announcements from one device.

The callback is given each announcement from peer_ip after the claiming module has completed it, so it sees what wait_for_channel() would return. It observes the announcement — a subscriber cannot change what other subscribers, or wait_for_channel(), are given. The callback is invoked on the Reactor thread, so any blocking behavior in that callback will delay any other callbacks scheduled there.

Call unregister with the handle returned here to release the reference to your callback function.

Returns: Handle identifying the registration to unregister().

Parameters

peer_ip
std::string

Address of the device to subscribe to.

callback
std::function<void(const EnumerationMetadata &)>

Invoked with each completed announcement, executed within the Reactor thread.

register_all

EnumerationCallbackHandle hololink::module::Adapter::register_all(
std::function<void(const EnumerationMetadata &)> callback
)

Subscribe to announcements from every device.

As register_ip(), but without the address filter: the callback is given every announcement, each one completed by the module that claims it.

Returns: Handle identifying the registration to unregister().

Parameters

callback
std::function<void(const EnumerationMetadata &)>

Invoked with each completed announcement, executed within the Reactor thread.

unregister

void hololink::module::Adapter::unregister(
const EnumerationCallbackHandle &handle
)

Cancel a registration.

No announcement observed after this returns is delivered to the registration. A callback already running is not interrupted.

Parameters

handle
const EnumerationCallbackHandle &

A handle returned by any of the register_* calls. Cancelling a registration that is not currently registered has no effect.

get_module

std::shared_ptr<Module> hololink::module::Adapter::get_module(
const EnumerationMetadata &metadata
)

Return the Module that provides services for an announced device.

The device is identified by the “fpga_uuid” and, where present, “compat_id” fields of its announcement.

Returns: The module that claims the device.

Throws: std::runtime_error if metadata carries no “fpga_uuid”, or if no installed module claims the device.

Parameters

metadata
const EnumerationMetadata &

An announcement, e.g. returned from wait_for_channel().

use_sensor

void hololink::module::Adapter::use_sensor(
int64_t sensor_number
)

Select which sensor of a device to use.

Enumeration provides information about a data path available with a device, and by default, that data path is usually associated with a specific sensor on that device. This API allows the application to indicate that it wants that data path to connect with a different sensor.

Throws: std::runtime_error if no installed module claims the device, the module does not support selecting a sensor, or if the sensor_number value is invalid.

Parameters

metadata
EnumerationMetadata &

Announcement to rewrite in place.

sensor_number
int64_t

Zero-based index of the sensor to describe.

Example

// Ordinary data-plane discovery.
auto& adapter = hololink::module::Adapter::get_adapter();
std::string hololink_ip = "192.168.0.2";
std::chrono::seconds discovery_timeout(30);
hololink::module::EnumerationMetadata metadata =
adapter.wait_for_channel(hololink_ip, discovery_timeout);
// Use this specific sensor port on the device.
int64_t sensor_number = 1;
adapter.use_sensor(metadata, sensor_number);
// Now use this configured metadata with e.g. RoceReceiver
// or sensor objects
// ...

use_mtu

void hololink::module::Adapter::use_mtu(
uint32_t mtu
)

Set the data-plane MTU.

Similar to use_sensor, this setting configures the MTU to be used in data-plane packets transmitted by HSB. Note that setting a value larger than what can be supported through all links in the network will likely result in dropped packets and that the host system likely needs to have a larger MTU configured in the receiver network interface.

Throws: std::runtime_error if no installed module claims the device, or if the module does not support setting the MTU.

Parameters

metadata
EnumerationMetadata &

Announcement to rewrite in place.

mtu
uint32_t

Data-plane MTU, in bytes.

use_multicast

void hololink::module::Adapter::use_multicast(
std::string address,
uint16_t port
)

Configure the data-plane to transmit to a multicast IP destination address.

This setting directs the data plane to transmit to the given destination address; this also enables the host data-plane receiver with calls to IP_ADD_MEMBERSHIP.

Note that for ROCE RDMA traffic, QP and RKEY mismatches will cause received RDMA traffic to be rejected; so multicast is only expected to work for a single RDMA host. Non-RDMA hosts (e.g. LinuxReceiver) currently do not check QP or RKEY values, so any number of LinuxReceiver hosts can receive traffic sent this way.

Throws: std::runtime_error if no installed module claims the device, or if the module does not support multicast.

Parameters

metadata
EnumerationMetadata &

Announcement to rewrite in place.

address
std::string

Multicast group address.

port
uint16_t

UDP port of the multicast group.

set_module_directory

void hololink::module::Adapter::set_module_directory(
std::filesystem::path dir
)

Configure the directory where hololink_module shared objects are located.

Applies to every lookup that follows, so call it before the device is announced — in practice, before wait_for_channel(). With no directory set, HOLOLINK_MODULE_DIR names one; failing that, the modules installed alongside the host are used, so an application running against an installed build needs neither.

Parameters

dir
std::filesystem::path

Directory holding the modules to load.


Static methods

get_adapter

static Adapter & hololink::module::Adapter::get_adapter()

Return the process-wide Adapter singleton.

Returns: The Adapter, valid for the lifetime of the process.