AXM  Protocol
Genesis kernel Core hub
Chat spoke Show spoke Embodied spoke
AXM Ecosystem  ·  Robotics Spoke  ·  v0.1

Embodied.No Gaps.
No Exceptions.
No Editing.

axm-embodied seals robot sensor streams using the same Genesis shard format as every other AXM spoke. The difference is REQ 5: the binary frame sequence in cam_latents.bin must be gap-free and monotone. Any discontinuity is a cryptographic failure.

Format
AXLF / AXLR
REQ 5
Non-Selective
On Gap
E_BUFFER_DISCONTINUITY
On Absent
Silent PASS
§01

Why Non-Selective Recording

An embodied system that selects which sensor frames to record is not trustworthy. The value of a verifiable record depends entirely on its completeness. A record that contains only the moments the system chose to preserve is worthless as evidence.

axm-embodied enforces this at the protocol level. The verifier does not ask whether the stream looks complete. It reads every frame_id in sequence and rejects on the first gap.

Rule I

Record everything, then seal. The hot buffer appends AXLR frames at sensor rate with no cryptographic overhead. When the session ends — or a power-safe threshold fires — Forge compiles the buffer into a sealed shard. Genesis signs it. Nothing is selected.

Rule II

A gap is a failure, not an omission. E_BUFFER_DISCONTINUITY is not a warning. It is a hard verification failure. The same exit code as a bad cryptographic signature. A robot that drops frames is not conformant. The stream format does not accommodate gaps.

Rule III

Offline verification, no infrastructure. axm-verify reads cam_latents.bin directly. It checks AXLF magic, then scans every AXLR record. The check is deterministic and stateless. It runs on the same machine that sealed the shard or any other machine with the publisher key.

Rule IV

Document shards pass silently. If cam_latents.bin is absent, REQ 5 does not apply. axm-chat, axm-show, and any document spoke are not affected. REQ 5 is a conditional requirement — it fires only when the file is present.

§02

Shard Format

The embodied shard is structurally identical to every other AXM shard. Same manifest.json. Same graph/ and evidence/ Parquet tables. Same Merkle tree. Same ML-DSA-44 signature. The only embodied-specific addition is content/cam_latents.bin.

shard_blake3_<merkle_root>/
  manifest.json ← merkle root + suite
  sig/
    manifest.sig ← ML-DSA-44
    publisher.pub
  content/
    session.jsonl ← structured event log
    cam_latents.bin ← REQ 5 applies
  graph/
    entities.parquet
    claims.parquet
    provenance.parquet
  evidence/
    spans.parquet
  ext/ ← optional, Merkle-covered
    episodes@1.parquet
    kinematics@1.parquet
    telemetry@1.parquet
manifest.json — same as all spokes

spec_version, shard_id, metadata, publisher, sources (with SHA-256 of every content file including cam_latents.bin), integrity.merkle_root, suite. The cam_latents.bin SHA-256 is in sources — the Merkle tree covers it like any other content file.

session.jsonl — structured event log

Newline-delimited JSON event records from the session: motor commands, state transitions, error conditions, external events. Byte-addressable via spans.parquet. Claims in graph/ can trace to specific JSON records.

cam_latents.bin — hot stream (REQ 5)

Binary file. AXLF magic header (8 bytes). Followed by a sequence of AXLR records in frame_id order. Records must be gap-free and monotone. Any missing frame_id triggers E_BUFFER_DISCONTINUITY. The file is Merkle-covered — its SHA-256 is in sources.

ext/kinematics@1.parquet — optional extension

Structured kinematic data extracted from the session: joint angles, velocities, forces, end-effector positions. Merkle-covered as an extension table. Queryable via axm-core Spectra without an LLM.

§03

AXLF / AXLR Binary Format

cam_latents.bin is a simple binary container. The file begins with an AXLF header block. The remainder of the file is a sequence of AXLR records in frame_id ascending order. No index. No random access. Scanned linearly by axm-verify.

AXLF Header Block
0x00–0x03 AXLF magic 4 bytes
0x04 version uint8 = 1
0x05–0x08 frame_id uint32 LE first frame
0x09–0x0C length uint32 LE payload bytes
REC_HEADER_FMT = "<4sBII"  ·  REC_HEADER_LEN = 13  ·  LATENT_DIM = 256
AXLR Record (per frame)
+0x00–0x03 AXLR magic 4 bytes
+0x04 version uint8 = 1
+0x05–0x08 frame_id uint32 LE monotone ↑
+0x09–0x0C length uint32 LE payload bytes
+0x0D–… payload length bytes · latent vector
axm_embodied/writer.py — frame writer
# Hot buffer write path — no crypto overhead, nanosecond appends
import struct, time

AXLF_MAGIC = b"AXLF"
AXLR_MAGIC = b"AXLR"

class HotBufferWriter:
    def __init__(self, path: str, session_ts: int = None):
        self._f = open(path, "wb", buffering=0)   # O_DIRECT writes
        self._frame_id = 0
        ts = session_ts or int(time.time() * 1_000_000)
        # Write AXLF header
        self._f.write(AXLF_MAGIC)
        self._f.write(struct.pack("<BII", 1, 0, ts))

    def append(self, payload: bytes) -> int:
        ts = int(time.time() * 1_000_000)
        self._f.write(AXLR_MAGIC)
        self._f.write(struct.pack("<BII", 1, self._frame_id, len(payload)))
        self._f.write(payload)
        fid = self._frame_id
        self._frame_id += 1
        return fid

    def close(self):
        self._f.flush(); self._f.close()

# Usage: one append per sensor tick. No batching. No buffering in userspace.
# On session end, call axm-embodied seal → Forge → Genesis signs.
§04

REQ 5 — Non-Selective Recording

REQ 5 is the only conformance requirement unique to embodied spokes. It is enforced by step 7 of axm-verify. The check is binary: either the frame sequence is gap-free or the shard fails verification.

E_BUFFER_DISCONTINUITY
Frame gap, bad magic, or truncation in cam_latents.bin

Triggered when: (1) AXLF magic is absent or wrong, (2) any AXLR record has magic mismatch, (3) any frame_id skips — expected N, found M where M ≠ N+1, (4) file truncates mid-record. All four conditions produce the same error code and the same verification outcome: FAIL, exit 1.

axm_verify/checks/stream.py — REQ 5 implementation
# Step 7 of axm-verify — hot stream continuity check
import struct
from pathlib import Path
from axm_verify.const import E_BUFFER_DISCONTINUITY

AXLF_MAGIC = b"AXLF"
AXLR_MAGIC = b"AXLR"
AXLF_HDR   = 32   # bytes
AXLR_HDR   = 24   # bytes (before payload)

def check_stream_continuity(shard_dir: Path) -> list[str]:
    cam = shard_dir / "content" / "cam_latents.bin"
    if not cam.exists():
        return []   # absent = silent pass (REQ 5 not applicable)

    errors = []
    with cam.open("rb") as f:
        hdr = f.read(AXLF_HDR)
        if len(hdr) < AXLF_HDR or hdr[:4] != AXLF_MAGIC:
            return [E_BUFFER_DISCONTINUITY]   # bad magic = immediate fail

        expected_frame_id = 0
        while True:
            rec_hdr = f.read(AXLR_HDR)
            if not rec_hdr:
                break   # EOF
            if len(rec_hdr) < AXLR_HDR or rec_hdr[:4] != AXLR_MAGIC:
                errors.append(E_BUFFER_DISCONTINUITY); break

            frame_id, _, payload_len = struct.unpack_from("<QQI", rec_hdr, 4)
            if frame_id != expected_frame_id:
                errors.append(E_BUFFER_DISCONTINUITY); break   # gap detected

            f.seek(payload_len, 1)   # skip payload
            expected_frame_id += 1

    return errors

# Test: synthetic gap
# Write frames 0,1,2 then skip to 4 → E_BUFFER_DISCONTINUITY fires on frame 4
tests/test_conformance.py — REQ 5 test
def test_req5_buffer_gap_detected(tmp_path):
    # Build a syntactically valid cam_latents.bin with a deliberate gap
    cam = tmp_path / "cam_latents.bin"
    with cam.open("wb") as f:
        f.write(b"AXLF")
        f.write(struct.pack("<IQQI", 1, 4, 0, 0))
        for fid in [0, 1, 2, 4]:   # gap: frame 3 missing
            payload = f"frame_{fid}".encode()
            f.write(b"AXLR")
            f.write(struct.pack("<QQI", fid, 0, len(payload)))
            f.write(payload)

    errors = check_stream_continuity(tmp_path.parent)
    assert "E_BUFFER_DISCONTINUITY" in errors   # ← must fire

PASSED · test_req5_buffer_gap_detected
§05

Verification Pipeline

axm-verify runs seven steps in sequence. Steps 1–6 are identical to all AXM spokes. Step 7 is the embodied-specific stream continuity check. A failure at any step halts and returns exit 1.

Step Name Pass Condition Error Code Scope
01 Layout manifest.json, sig/, content/, graph/, evidence/ present E_LAYOUT_MISSING
E_LAYOUT_DIRTY
All Spokes
02 Manifest Parse Valid JSON, required fields present, ≤256 KiB E_MANIFEST_SYNTAX
E_MANIFEST_SCHEMA
All Spokes
03 Trusted Key + Signature publisher.pub matches --trusted-key; signature verifies E_SIG_MISSING
E_SIG_INVALID
All Spokes
04 Merkle Root Computed root == manifest.integrity.merkle_root E_MERKLE_MISMATCH All Spokes
05 Parquet Schema Column names, types, counts match frozen Arrow schemas E_SCHEMA_TYPE
E_SCHEMA_NULL
All Spokes
06 Reference Integrity All claim subjects, span sources, byte ranges valid E_REF_ORPHAN
E_REF_SOURCE
All Spokes
07 Stream Continuity cam_latents.bin absent OR AXLF valid AND all frame_ids gap-free E_BUFFER_DISCONTINUITY Embodied Only
§06

Conformance Requirements

Spokes must satisfy REQ 1–4 to be conformant with the Genesis spec. Embodied spokes must additionally satisfy REQ 5. Run all 13 conformance tests; the REQ 5 test is test_req5_buffer_gap_detected.

REQ Description Error Codes Scope
REQ 1 Manifest integrity — byte-exact signature over manifest E_SIG_INVALID
E_MERKLE_MISMATCH
All Spokes
REQ 2 Content identity — all content files covered by Merkle tree E_MERKLE_MISMATCH
E_REF_SOURCE
All Spokes
REQ 3 Lineage events — all references valid, no nulls in required columns E_REF_ORPHAN
E_SCHEMA_NULL
All Spokes
REQ 4 Proof bundle — valid signature from trusted publisher key E_SIG_INVALID
E_SIG_MISSING
All Spokes
REQ 5 Non-selective recording — no gaps in binary hot stream E_BUFFER_DISCONTINUITY Embodied Only
§07

Quick Start

Install
# Install dependencies in order
pip install -e ./axm-genesis    # kernel
pip install -e ./axm-core       # runtime
pip install -e ./axm-embodied   # this spoke
Record + Seal
# Start a session (opens cam_latents.bin)
axm-embodied record start \
  --signing-key keys/robot.pem

# Frames append at sensor rate
# On session end, Forge seals the shard
axm-embodied record stop
✓ Sealed ~/.axm/shards/session-<id>/
Verify
# Verify a sealed session shard
axm-verify shard \
  ~/.axm/shards/session-abc123/ \
  --trusted-key keys/robot.pub

{"status":"PASS","error_count":0,"errors":[]}

# Introduce a gap → should FAIL
axm-verify shard ./test-gap-shard/ \
  --trusted-key keys/robot.pub

{"status":"FAIL","errors":["E_BUFFER_DISCONTINUITY"]}
Conformance Suite
# Run all 13 conformance tests
python -m pytest \
  tests/test_conformance.py -v

test_baseline_gold_shard_passes ....... PASSED
test_req5_buffer_gap_detected ......... PASSED
test_req5_bad_magic_detected .......... PASSED
test_req5_truncation_detected ......... PASSED
13 passed in 0.84s