Skip to content

Raw SDK Primitives

While the TrainingLoop API provides a convenient wrapper, it is a thin layer over the OmniLoop SDK primitives. You can call these primitives directly for full control over your execution flow and telemetry.

Use the raw primitives when:

  • You need to integrate OmniLoop into an execution flow you cannot easily restructure (e.g., a C++ engine calling into Python).
  • You need fine-grained control over exactly what gets published and when.
  • You do not have a centralized configuration dataclass to derive a schema from.

When using raw primitives, you must manually define your parameter schema, block on halts, poll for mutations, and publish telemetry.

import json
from omniloop import tracker, load_param_schema
# 1. Define schema
load_param_schema("my_params.yaml") # or use declare_param(...)
for epoch in range(num_epochs):
# 2. Pause point: block if the dashboard has halted the loop
tracker.wait_if_halted()
# 3. Apply dashboard edits
mutations = tracker.get_mutations()
if "learning_rate" in mutations:
lr = float(mutations["learning_rate"])
# ... your application logic ...
# 4. Publish telemetry
tracker.publish_telemetry_raw(json.dumps({
"learning_rate": lr,
"reward_mean": reward_mean,
# ... other state ...
}))
Method Description
tracker.wait_if_halted() The halt barrier. Call once per iteration. Blocks until resumed under the default block policy; returns immediately under handoff/advisory, where the caller reads poll_halt() instead.
tracker.poll_halt() Non-blocking barrier. Returns action (run / run_safety / released), halted, reason, escalation, halted_for_ns — all as strings. run_safety means: run your fallback controller this iteration, not the loop body.
tracker.set_halt_policy(p) "block", "handoff" or "advisory". Local-only by design — no IPC command sets it, so a remote operator cannot make a hardware loop freeze its own control thread.
tracker.step_barrier() Consume single-step mode. Call only after an iteration that ran the real loop body.
tracker.set_halted(halted, reason=None) Halt or release, optionally recording operator / watchpoint / exception / step.
tracker.get_mutations() -> dict Returns parameter edits from the dashboard since the last call. Keys are parameter names; values are strings.
tracker.publish_telemetry_raw(json_str) Publishes a JSON-encoded state snapshot to the shared-memory channel.
tracker.register_variable_pointer(name, addr, var_type) Register a raw memory pointer for zero-copy reflection.
Method Description
tracker.add_watchpoint(name, condition, threshold) Arms a conditional halt (e.g., halt if a metric exceeds a threshold).
tracker.set_watch_all_nonfinite(bool) Automatically halts the loop on any NaN or inf value.
tracker.stats() -> dict Returns IPC health counters.
tracker.dump_flight_recorder(path) Dumps the black box ring buffer to disk.
tracker.set_flight_recorder_capacity(n) Sets the capacity of the ring buffer.
tracker.state_hash(exclude=[...]) -> int Hashes the registry’s canonical state to help detect divergence.

wait_if_halted() is policy-dependent, which matters most for the loops that use these primitives — they are usually the ones closest to hardware. A raw loop that must not stop looks like this:

tracker.set_halt_policy("handoff")
for _ in range(steps):
decision = tracker.poll_halt()
if decision["action"] == "run_safety":
damping_hold() # halted: keep commanding the machine
else:
controller_update() # running normally
tracker.step_barrier() # spend a step only on a real iteration
tracker.publish_telemetry_raw(json.dumps(state))

Note that poll_halt() returns strings, and halted is Rust’s lowercase "true"/"false" — not Python’s "True". Compare case-insensitively.

See Halt & Step for the policies, halt reasons, and the deadman.

If you run multiple concurrent instances of your application, you must isolate their OmniLoop sessions to prevent IPC collisions.

  • Set the OMNILOOP_SESSION_ID environment variable before starting your process.
  • Alternatively, use the CLI wrapper which handles this automatically:
Terminal window
omniloop up --session my_run