Skip to content

Wire Format Reference

Nate Howard edited this page Mar 11, 2026 · 1 revision

Wire Format Reference


Version 1 Header (56 bytes)

The original VIRP wire format. Signs the payload and core metadata.

 0                   1                   2                   3
 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|    Version    |     Type      |            Length             |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                           Node ID                             |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|    Channel    |     Tier      |           Reserved            |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                        Sequence Number                        |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                    Timestamp (nanoseconds)                    |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                    HMAC-SHA256 (32 bytes)                     |
|                                                               |
|                                                               |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

Trust guarantee (v1): Payload authentic — the AI cannot fabricate what it saw.


Version 2 Header — Context Binding

Version 2 extends the HMAC boundary to include session context, device identity, and command identity.

typedef struct {
    uint8_t  version;           /* VIRP_VERSION_2 = 2              */
    uint8_t  channel;           /* VIRP_CHANNEL_OBS / INTENT       */
    uint8_t  tier;              /* GREEN / YELLOW / RED / BLACK    */
    uint8_t  _reserved;         /* must be zero                    */

    uint64_t node_id;           /* stable O-Node identity          */
    uint64_t timestamp_ns;      /* nanoseconds since Unix epoch    */
    uint64_t seq_num;           /* monotonically increasing        */

    uint8_t  session_id[16];    /* from SESSION_BIND               */
    uint64_t device_id;         /* stable device UUID              */

    uint8_t  command_hash[32];  /* SHA-256 of canonical command    */
    uint32_t payload_len;       /* bytes of observation payload    */
} virp_obs_header_v2_t;

Trust guarantee (v2): Payload + context authentic — the AI cannot fabricate the source, session, or command.


Trust Guarantee Comparison

Version What Is Signed What Can Be Proven
v1 payload + core header This payload is authentic
v2 payload + core header + session_id + device_id + command_hash This exact device, in this exact session, responding to this exact command, produced this payload

What a v2 Observation Proves

A valid v2 HMAC is a cryptographic commitment to all of the following simultaneously:

node_id        — which O-Node collected it
session_id     — which negotiated session it belongs to
device_id      — which device was queried
command_hash   — which exact command was executed
timestamp_ns   — when it was collected
seq_num        — its position in the chain (gaps detectable)
payload        — what the device returned

If any field is altered after signing, HMAC verification fails. There is no way to reassign a valid observation to a different device, command, or session.


Signing

HMAC_SHA256(
    session_key,                  /* derived per-session key      */
    (uint8_t *)&hdr,              /* sizeof(virp_obs_header_v2_t) */
    payload,                      /* raw device output            */
    payload_len,
    signature_out                 /* 32 bytes                     */
);

Note: session_key is used — not the master observation key. The master key derives the session key at handshake time via HKDF and never directly signs a runtime observation.


Canonical Command Hashing

command_hash = SHA-256(canonical_command_string)

Canonicalization rules (applied in order):

Step Rule
1 Trim leading and trailing whitespace
2 Collapse repeated internal spaces to single space
3 Normalize line endings to \n
4 Strip CLI prompts and transport-specific wrappers

Example:

Input:   "  show ip bgp summary\r\n"
Output:  "show ip bgp summary"
Hash:    SHA-256("show ip bgp summary") = 7c2b4d3a...

The same logical command always produces the same hash regardless of how whitespace or line endings vary between vendors or transport layers.


Canonical Device Identity

device_id is a stable uint64_t UUID assigned at device onboarding and stored in devices.json.

Rules:

  • Device display names and hostnames MUST NOT be used as device_id
  • Renaming a device MUST NOT change its device_id
  • device_id is assigned once at onboarding and never changes

This ensures the cryptographic record remains stable across configuration changes, hostname updates, and IP address changes.


Channel Values

Value Name Purpose
0x01 OBSERVATION Read-only device state collection
0x02 INTENT Proposed configuration changes

Trust Tier Values

Value Name Meaning
0x01 GREEN No approval required — read-only
0x02 YELLOW Flagged for review
0x03 RED Human approval required
0xFF BLACK Blocked at C level — never reaches device

Backward Compatibility

Nodes SHOULD accept both v1 and v2 during transition periods. The negotiated session version (from HELLO/HELLO_ACK) determines which format is used for the session.

A v1 node connecting to a v2 O-Node will negotiate down to v1 during the handshake. A v2 node connecting to a v1 O-Node will do the same.


Full Specification

See VIRP-WIRE-FORMAT.md and VIRP-SPEC-RFC-v2.md in the repository root.

Clone this wiki locally