Resource Control
Librux resource control is the operating model for managed subsystem processes. It is not a global Linux sandbox and it does not block every process a user can start from a shell. It applies when a subsystem is launched as a managed package through Librux.
Use this page after you understand Runtime Configuration, CLI Tools, and the normal service model. For runnable checks, see Add Resource Policy. For the package layout itself, see Subsystem Packages.
Operating Model
A managed launch has four stages.
- a package declares the resources it needs
librux-resourced.serviceaccepts or rejects the claim- the launcher starts the process only after a lease is granted
- the lease is released only after the managed process scope is gone
Resource guarantees apply only to managed package launches.
librux launch run ./dist/my_controller.libruxpkg --detach
Web Console Runtime launches use the same detached service-owned path. Package
installation only stores and validates reusable packages; Runtime creates the
running subsystem instance. When a package is launched, resource admission,
environment injection, affinity, brokered FD policy, and cgroup placement match
librux launch run --detach.
For role: app packages installed from the Web Console Packages page and
launched from Runtime, the application boundary is stricter than a generic
subsystem package.
- the package must set
resources.sandbox.network: brokered - the application subsystem must not claim NIC, link-layer, CAN, serial, or device resources
- browser UI must be packaged as static
frontendassets and served from/api/v1/packages/<package-id>/ui/
This prevents managed application code from self-hosting a native HTTP or
WebSocket frontend with direct AF_INET, AF_INET6, or AF_PACKET sockets.
If a package needs a browser-facing REST or WebSocket backend for its packaged
static UI, declare frontend.context.api or frontend.context.ws in
package.yaml and open the corresponding listener through the resource broker
with open_frontend_tcp_listener. Application subsystems talk to the robot through compound
capability bindings; hardware and field resources stay behind gateways and
components.
Runtime Configuration
Resource authority is configured under resource_service.
resource_service:
mode: "auto" # auto, required, or disabled
# socket_path: "/run/librux/resourced.sock"
| Mode | Operator meaning |
|---|---|
auto |
Use librux-resourced when reachable and allow local ownership fallback where the runtime permits it. This is the default install posture. |
required |
Treat the resource service as mandatory. Managed launches fail when the resource service is unavailable. |
disabled |
Disable the managed resource authority path. Managed app start/stop through the control backend is not available. |
For appliance or managed robot hosts, prefer required once service setup and
resource policy are validated. Keep auto while bringing up a new host or
debugging a development install.
Service Checks
Installed product hosts should have the resource service running.
. <prefix>/env.sh
librux system status
librux resource status
librux resource inventory
The default Linux service socket is this.
/run/librux/resourced.sock
Installed system services prepare /run/librux as root:librux with mode
2770. The non-root librux-control.service user can create its control socket
there, while resource-service access remains limited to the Librux runtime group.
If services were not installed, install them from the selected prefix.
sudo <prefix>/bin/librux system install --prefix <prefix>
Adjust socket/client policy when needed.
sudo <prefix>/bin/librux system install \
--prefix <prefix> \
--resource-group librux \
--client-user robot \
--socket-mode 0660
Install serial/USB device policy when managed packages need device-node access.
sudo <prefix>/bin/librux-device-policy-install \
--device-group librux-device \
--device-mode 0660
Operators should not add normal users to the Librux device group. Device access
should be granted per managed package process by librux-resourced.
Managed Launch Lifecycle
Validate and build a package.
librux package validate ./my_controller
librux package build ./my_controller \
--out ./dist/my_controller.libruxpkg \
--force
Run it under resource control.
librux launch run ./dist/my_controller.libruxpkg \
--config <prefix>/runtime/config.yaml
Detached launch and lease inspection.
librux launch run ./dist/my_controller.libruxpkg --detach
librux resource status
librux launch status <lease-id>
librux resource stop <lease-id>
Reusable packages can be launched as named instances when their package manifest declares the corresponding parameters.
librux launch run ./dist/manipulator_servo.libruxpkg \
--instance demo.left_manipulator \
--set subsystem.name=demo.left_manipulator \
--set controller.robot_id=left_ps_ca \
--runtime-dir /run/librux/packages/demo.left_manipulator \
--detach
The launcher rejects --set keys that are not declared by the package. This
keeps resource admission and command shape controlled by the package manifest.
By default, installed packages use the prefix state root such as
/opt/librux/var/run/packages/<instance-id> for runtime files. Source checkout
packages without an installed prefix fall back to package-local
var/instances/<instance-id>. Explicit relative runtime dirs stay
package-local. Explicit absolute runtime dirs are limited to /run/librux or
temporary directories because librux-resourced may create them from a
service-owned launch path.
Package Resource Declaration
A managed package declares resource requirements in package.yaml.
schema_version: 1
name: control.arm_controller
entrypoint:
command: bin/controller
args: ["--config", "config/controller.yaml"]
resources:
cpu:
cores: [2, 3]
exclusive: true
network:
interfaces:
- name: enp4s0
mode: shared
policy: control-plane
link_layer:
interfaces:
- name: enp5s0
mode: exclusive
access: raw_packet
protocols: [ethercat]
grant:
capabilities: [CAP_NET_RAW]
devices:
paths:
- /dev/ttyUSB0
can:
- can0
sandbox:
network: brokered
can: brokered
devices: managed
The entrypoint is resolved from the package directory unless it is absolute. Relative paths cannot escape the package directory.
Resource Semantics
| Resource | Semantics |
|---|---|
| CPU | affinity is the minimum guarantee; cgroup v2 cpuset placement is used when available |
| NIC | IP networking claim for selected adapters; brokered network mode can deliver accepted UDP/TCP sockets |
| Link-layer NIC | exclusive raw Ethernet fieldbus claim for EtherCAT, CC-Link IE TSN, Profinet RT, or custom L2 protocols |
| CAN | SocketCAN interface claim, treated as an exclusive outlet resource |
| Serial / TTY | exclusive device-node claim for /dev/ttyUSB*, /dev/ttyACM*, /dev/ttyAMA*, /dev/ttyS*, and similar paths |
| Device nodes | managed device FDs can be delivered by the resource service |
resources.network.interfaces and resources.link_layer.interfaces both name
Linux network interfaces, but they describe different authority models.
network is for IP socket policy. link_layer is for packages that need direct
AF_PACKET raw Ethernet access, such as a SOEM EtherCAT gateway.
Link-layer claims are exclusive and conflict with ordinary network claims on the
same interface. They are also incompatible with resources.sandbox.network.
brokered, because brokered network mode intentionally blocks direct
AF_PACKET socket creation.
The launch report separates affinity from cgroup placement. Treat
attach.affinity_applied=true as the minimum CPU result. If
attach.cgroup_degraded=true, the process is pinned by affinity but strict
cpuset containment was not available on that host.
Link-Layer Raw Packet Grants
Some industrial Ethernet stacks need raw Ethernet access and cannot receive a pre-opened UDP/TCP/CAN FD. EtherCAT through SOEM is the common example because SOEM opens and drives the packet socket inside the gateway process.
For this class of gateway, librux-resourced keeps admission and ownership
centralized but does not relay fieldbus packets.
- the package declares an exclusive
resources.link_layer.interfacesclaim librux-resourcedrejects conflicting claims for the same NIC- the managed child is launched with the requested bounded capability, normally
CAP_NET_RAW - the gateway opens its raw packet socket directly and owns the realtime data path
Supported protocol labels are ethercat, cclink_ie_tsn, profinet_rt, and
custom_l2. The current grant allowlist is CAP_NET_RAW and CAP_NET_ADMIN.
Use CAP_NET_ADMIN only when the gateway must configure the interface itself.
Brokered Handles
Brokered modes prevent common direct resource bypasses inside managed packages and deliver accepted handles through the resource broker.
Supported brokered paths.
- network sockets with
resources.sandbox.network - brokered - SocketCAN with
resources.sandbox.can - brokered - device nodes with
resources.sandbox.devices - managed
Link-layer raw packet access is intentionally not a brokered handle in this release. It is a lease plus launch-time capability grant so EtherCAT-class control loops do not pay a per-packet resource-service hop.
In brokered mode, the launched process receives.
LIBRUX_RESOURCE_LEASE_ID
LIBRUX_RESOURCE_SERVICE_SOCKET
LIBRUX_CONTROL_SOCKET
The SDK asks librux-resourced for a resource handle. The service verifies the
live lease, opens the accepted socket or device, applies host policy such as
SO_BINDTODEVICE where needed, and transfers the FD with SCM_RIGHTS.
The data path then uses the received FD directly; traffic does not route through the control backend.
LIBRUX_CONTROL_SOCKET is separate from brokered resource handles. It points to
the host-local control backend Unix domain socket, normally
/run/librux/control.sock, and is used by SDK lifecycle, heartbeat, Event slot
request, and Procedure/Operation registration messages. This keeps SDK runtime
bookkeeping available even when a package sandbox blocks direct AF_INET
socket creation under resources.sandbox.network: brokered.
Stop And Cleanup
stop is a bounded termination path, not a guarantee that the app handles
SIGTERM. Librux first sends SIGTERM to give the managed process scope a
short cleanup opportunity. If any live process remains after the grace window,
the runtime escalates to SIGKILL and only marks the lease released after the
process scope is gone.
Runtime Graph and lbx subsystem expose this as process terminate. Force
kill is a separate operator action that skips the SIGTERM grace window and
sends SIGKILL immediately.
The stop report is factual.
signal_sent=truemeans the graceful stop signal was sent.kill_sent=truemeans the process scope did not exit during the grace window and Librux usedSIGKILL.graceful=truemeans the scope exited withoutSIGKILL.stop_methodrecords the observed stop path, such assigterm,sigkill,already_dead, orno_process.
For Python and other runtimes, application-level signal handling is best effort. Handlers can be delayed by blocking calls, native extensions, wrapper shells, or worker child processes. Managed app stop should therefore be treated as process-scope termination, not as application-level SIGTERM acknowledgement.
Direct Execution
During development, a subsystem can still be run directly from a shell, IDE, or debugger. Librux does not globally block ordinary Linux process execution.
If the process uses the Librux SDK, direct execution still registers a subsystem session with the control backend. That registration is for subsystem identity, routing, and lifecycle diagnostics; it is not a resource-control lease.
Direct execution is not a managed launch. The process does not receive.
- a resource lease
- managed environment injection
- CPU/cgroup placement
- brokered NIC/CAN/TTY/device FDs
- link-layer capability grants such as
CAP_NET_RAW - Web Console lifecycle ownership
Resource-control guarantees apply only when the subsystem is started through
librux launch, librux deploy, or a managed Runtime launch in the Web Console.
Product deployments that must prevent unmanaged execution should enforce that
through host or appliance policy, including restricted shell access, root policy,
device permissions, udev policy, and service ownership.
Use librux subsystem status, librux subsystem sessions, and
librux subsystem cleanup <name> --stale to inspect or clear subsystem
lifecycle state during repeated direct-run development.
Validation
Use Add Resource Policy for reproducible checks covering.
- CPU lease smoke
- brokered NIC sockets
- link-layer raw packet launch grants
- brokered SocketCAN
- brokered TTY device FDs