Live Agent working · engine-01 Placer/router engine positioning
DC-03 — API Reference

API Reference

WebSocket HID protocol, REST API endpoints, and UART wire format.

* * *
WebSocket HID Protocol

The browser connects to the KVMD WebSocket endpoint to send keyboard and mouse events. Messages are JSON objects dispatched to the UART HID bridge.

Endpoint
ws://<host>:8080/ws
Keyboard Events
// Key press
{"type": "key", "code": "KeyA", "state": true}

// Key release
{"type": "key", "code": "KeyA", "state": false}

// Paste text as keystrokes
{"type": "paste", "text": "hello world"}
Mouse Events
// Relative mouse move
{"type": "mouse_move", "dx": 10, "dy": -5}

// Mouse button (button: 0=left, 1=right, 2=middle)
{"type": "mouse_button", "button": 0, "state": true}

// Scroll wheel
{"type": "mouse_scroll", "dy": -3}
* * *
REST API Endpoints
AT-01 ATX Control
GET /api/atx
Returns current ATX state (power LED, HDD LED status).
// Response
{"power": true, "hdd": false}
POST /api/atx/power
Short press power button (~200ms). Toggles power on/off.
POST /api/atx/power-long
Long press power button (~5s). Force power off.
POST /api/atx/reset
Pulse the reset line (~200ms). Hard reset the target machine.
VM-01 Virtual Media
GET /api/media
List available ISO images and current mount status.
// Response
{"images": ["alpine.iso", "ubuntu.iso"], "mounted": "alpine.iso"}
POST /api/media/upload
Upload an ISO image. Multipart form data with file field.
POST /api/media/download
Download a preset ISO from the internet. Body: {"preset": "alpine"}
POST /api/media/mount
Mount an ISO as a virtual CD-ROM drive. Body: {"image": "alpine.iso"}
POST /api/media/eject
Eject the currently mounted virtual CD-ROM.
VD-01 Video (WebRTC Proxy)
* /rtc/{path}
Proxies all requests to the go2rtc server (port 1984). This handles WebRTC signaling (SDP offer/answer) and stream negotiation. The browser's WebRTC player connects through this proxy for video.
* * *
UART Protocol Wire Format

Binary protocol between the Duo S (KVMD) and ESP32-S3 (HID bridge) over a 115200 baud UART link. The Python reference implementation is in software/sim/protocol.py; the Rust mirror is in firmware/esp32-hid-rs/kvm-protocol/.

Packet Format
┌──────────┬──────────┬───────────────┬──────────┐
│ type: u8 │ len: u8  │ payload: [u8] │ csum: u8 │
└──────────┴──────────┴───────────────┴──────────┘

Checksum = sum of all preceding bytes, masked to 8 bits (& 0xFF)
Command Types
Code Name Payload Description
0x01KEY_DOWN[modifier:u8][keycode:u8]Press a key
0x02KEY_UP[modifier:u8][keycode:u8]Release a key
0x03MOUSE_MOVE[dx:i16 LE][dy:i16 LE]Relative mouse movement
0x04MOUSE_BUTTON[button:u8][state:u8]Mouse button press/release
0x05MOUSE_SCROLL[dy:i8]Scroll wheel delta
0x06RESET(none)Reset HID state
Example Packets
# KEY_DOWN: press 'A' (keycode 0x04, no modifier)
# type=0x01, len=0x02, payload=[0x00, 0x04], csum=0x07
[01] [02] [00 04] [07]

# MOUSE_MOVE: dx=10, dy=-5 (little-endian i16)
# type=0x03, len=0x04, payload=[0x0A 0x00 0xFB 0xFF], csum=0x0B
[03] [04] [0A 00 FB FF] [0B]

# RESET: no payload
# type=0x06, len=0x00, csum=0x06
[06] [00] [06]
Modifier Byte
Bit Modifier Bit Modifier
0x01Left Ctrl0x10Right Ctrl
0x02Left Shift0x20Right Shift
0x04Left Alt0x40Right Alt
0x08Left GUI0x80Right GUI
* * *