13  The default stack

This part documents UnetStack’s services in the abstract and the concrete agents that implement them. Each service chapter follows the same shape: an Overview of the service, its Capabilities, the Messages it exchanges, its Parameters, worked Examples, and finally the Implementations section. This chapter is the orientation: it shows the agents that make up a node’s default stack — the set loaded automatically when a node boots — points you to where each one is documented, and describes the handful of messages that are common to the whole stack rather than to any single service.

13.1 What gets loaded

When a node starts, the agent providing the NODE_INFO service is created first, and the rest of the stack is then loaded by a setup.groovy script. If a user-supplied scripts/setup.groovy exists, it is run instead of the standard etc/setup.groovy — a full replacement, not a merge — so a node with its own setup script loads only the node agent, the shell agents, and (on a modem) the modem-side phy/bb agents, plus whatever the script itself adds. This is the supported way to run a custom stack. After setup, etc/startup.groovy runs, and chains to a scripts/startup.groovy if present — the right place for node-specific configuration (parameter settings) as opposed to stack composition. On a standard simulated or modem node, the default stack is:

Agent Class Services
node NodeInfo NODE_INFO
arp AddressResolution ADDRESS_RESOLUTION
ranging Ranging RANGING
mac CSMA MAC
uwlink ECLink LINK, DATAGRAM
router Router ROUTING, DATAGRAM
rdp RouteDiscoveryProtocol ROUTE_MAINTENANCE
caddy Caddy / CaddyLite TRANSPORT, REMOTE, DATAGRAM
usbl USBL DOA
tuner LinkTuner LINK_TUNING
scheduler Scheduler SCHEDULER
profiles Profiles
speedtest SpeedTest
bbmon BasebandSignalMonitor

The PHYSICAL, BASEBAND, LINK_TUNING and DOA services are not loaded by setup.groovy; they are provided by the modem. On a commercial modem they come from the modem firmware, which runs its own agents on the modem’s signal-processing hardware; in simulation the HalfDuplexModem agent stands in for the modem and provides PHYSICAL, BASEBAND and DOA (and a basic DATAGRAM service), modelling the channel so that the higher layers run unchanged. See Chapter 17, Chapter 27 and Chapter 26. The DOA and LINK_TUNING services may require a license and may be absent on some devices.

You can see the agents running on a node at any time with the ps command:

> ps
scheduler: org.arl.unet.scheduler.Scheduler
rdp: org.arl.unet.net.RouteDiscoveryProtocol
caddy: org.arl.unet.transport.Caddy
ranging: org.arl.unet.localization.Ranging
uwlink: org.arl.unet.link.ECLink
node: org.arl.unet.nodeinfo.NodeInfo
simulator: org.arl.unet.sim.SimulationAgent
phy: org.arl.unet.sim.HalfDuplexModem
bbmon: org.arl.unet.bb.BasebandSignalMonitor
arp: org.arl.unet.addr.AddressResolution
device: org.arl.unet.device.SimpleDevice
profiles: org.arl.unet.profiles.Profiles
router: org.arl.unet.net.Router
shell: org.arl.fjage.shell.ShellAgent
speedtest: org.arl.unet.utils.SpeedTest
mac: org.arl.unet.mac.CSMA

Each agent is reachable from the shell by its name (e.g. router), and any provider of a service can be located with agentForService (e.g. agentForService(Services.ROUTING)). The transport/remote agent is loaded under the name caddy, but is most often used through the transport and remote shell handles for the services it provides.

13.2 Where each agent is documented

Each agent’s protocol, parameters and usage notes are documented in the Implementations section of its service chapter. The table below indexes the services, their default providers, and the chapters that document them:

Service Default provider Chapter
NODE_INFO node (NodeInfo) Chapter 14
ADDRESS_RESOLUTION arp (AddressResolution) Chapter 15
DATAGRAM phy, uwlink, router, caddy Chapter 16
PHYSICAL phy (modem firmware / HalfDuplexModem) Chapter 17
BASEBAND bb/phy (modem firmware / HalfDuplexModem) Chapter 27
RANGING ranging (Ranging) Chapter 25
LINK uwlink (ECLink) Chapter 18
LINK_TUNING tuner (LinkTuner) Chapter 20
MAC mac (CSMA) Chapter 19
ROUTING router (Router) Chapter 21
ROUTE_MAINTENANCE rdp (RouteDiscoveryProtocol) Chapter 22
TRANSPORT caddy (Caddy/CaddyLite, via transport) Chapter 23
REMOTE caddy (Caddy/CaddyLite, via remote) Chapter 24
SCHEDULER scheduler (Scheduler) Chapter 29
DEVICE_INFO device (modem firmware / SimpleDevice) Chapter 28
DOA modem firmware / HalfDuplexModem Chapter 26
SHELL (fjåge) shell, websh (ShellAgent) Chapter 30

The utility agents profiles, speedtest and bbmon provide no service and are documented in Chapter 32.

Beyond the default stack, UnetStack ships additional agents you can load — alternative links and transports, modem drivers, and bridges to external systems. These are documented alongside the default agents in the relevant service chapters (e.g. the licensed optical and satellite links in Chapter 18, the Popoto modem driver in Chapter 17) and in Chapter 32.

13.3 Premium features

Almost everything in this handbook — the default stack, the services it provides, and the APIs you build against — is available in the community edition of UnetStack, which is free for non-commercial use. A handful of agents and features, however, are premium:

  • Some are part of a commercial product — for example, the PHYSICAL, BASEBAND and DOA services are provided by the firmware of a commercial modem, and are not part of the community edition. In simulation, the HalfDuplexModem agent stands in for this hardware so that the rest of the stack runs unchanged.
  • Others are licensed add-ons — optional agents that extend the stack with advanced functionality or higher performance (higher-throughput and non-acoustic links, prioritized/QoS transport, additional modem drivers, and so on) and require a license to enable.

Throughout the handbook, such agents and features are flagged with a premium feature callout that points back here. Where you see one, the feature is either part of a commercial product or available as a licensed upgrade. To find out what is available for your hardware, or to obtain a license, contact your modem vendor — or Subnero, who develop and commercially support UnetStack.

13.4 Common messages

A handful of messages are not tied to any one service — any agent in the stack may emit or respond to them. Because they belong to no single service chapter, they are collected here.

13.4.1 Parameter access

All parameter reads and writes — whether typed at the shell (phy.MTU), performed through a UnetSocket gateway, or made by one agent on another — are carried by a single pair of messages. A ParameterReq names the parameters to get (or set, with new values), along with an optional index for indexed parameters; the agent answers with a ParameterRsp carrying the resulting values. An empty ParameterReq asks for all of an agent’s parameters, which is exactly what the shell sends when you type a bare agent name (Chapter 3).

  • ParameterReq – get/set parameters of an agent

    Field Type Default Remarks
    index int -1 index for indexed parameters (-1 if not indexed)
    param string
    requests object[] list of parameters to get/set
    value object

The answering ParameterRsp mirrors the request: it carries the same index, and a map of each requested parameter to its (resulting) value, from which individual values are read with get(param).

When a parameter changes, the owning agent publishes a ParamChangeNtf on the Topics.PARAMCHANGE topic, letting other agents react to configuration changes (some agents, such as node, publish these notifications on their own topic instead — see Chapter 14).

13.4.2 Capability queries

Every agent can be asked which optional features it supports. A CapabilityReq that names a specific capability is answered with a CONFIRM or DISCONFIRM; one that names no capability is answered with a CapabilityListRsp enumerating all of the agent’s capabilities. The capabilities an agent may advertise are listed in the Capabilities section of the relevant service chapter.

  • CapabilityReq – query an agent’s capabilities

    Field Type Default Remarks
    cap string capability to query, or none to list all
  • CapabilityListRsp – list of an agent’s capabilities

    Field Type Default Remarks
    capSet string[] Any[]

13.4.3 Agent lifecycle

As agents are created and destroyed, the container publishes lifecycle notifications on the Topics.LIFECYCLE topic. Subscribing to it lets an application react to the set of agents currently running — for example, to pick up a newly loaded agent, or to notice one that has crashed. AgentStartNtf announces a newly started agent and the services it provides, AgentTerminationNtf a normal shutdown, and AbnormalTerminationNtf an unexpected crash (carrying the exception that caused it):

  • AgentStartNtf – an agent has started

    Field Type Default Remarks
    agentClassName string
    containerName string
    services string[] services the agent provides
  • AgentTerminationNtf – an agent has terminated normally

    Field Type Default Remarks
    agentClassName string
    containerName string
  • AbnormalTerminationNtf – an agent has crashed unexpectedly

    Field Type Default Remarks
    agentClassName string
    containerName string
    exception object the exception that caused the crash

All three extend a common AgentLifecycleNtf base class, so an agent can match on that to catch every lifecycle event regardless of kind.

13.4.4 System notifications

A SystemNtf carries a system-wide notification — a severity level, a human-readable description, and optional structured details — published on the Topics.SYSTEM topic.

  • SystemNtf – system-wide notification

    Field Type Default Remarks
    description string human-readable description
    details object optional structured details
    level string WARNING severity level

These messages result in log entries and shell notifications. For example:

> send new SystemNtf(recipient: topic(Topics.SYSTEM), description: 'important message!')
true
---
WARNING: important message!
---