Ryan Malloy 235ffc955c Add the recorded talk, a player, and the Supported Systems badge
The talk exists as audio now: a synthesised narration, four and a half
minutes, on a /talk/ page with the full transcript underneath. The transcript
is the authoritative version, and the audio is preload="none" so the 2.5 MB
file is only fetched if somebody presses play. A second player sits on the
homepage, the way spicebook surfaces its pitch.

The badge follows the homestar.ink pattern: a small webring-style button in
the footer that opens a short modal about the studio. It is a Starlight footer
override, so it appears site-wide rather than only on the landing page, and it
closes on Escape or backdrop click with focus returned to the badge.

Talk script and narration text are kept in drafts/ for reuse.
2026-08-18 14:43:16 -06:00
2026-08-16 22:03:16 -06:00

mcqemu

An MCP server that lets LLM agents manage QEMU virtual machines: launch and stop VMs, inspect them over QMP, manage disk images with qemu-img, take live snapshots, and run commands inside guests through qemu-guest-agent.

Requirements

  • Linux with QEMU installed (qemu-system-* and qemu-img on PATH)
  • /dev/kvm access for hardware acceleration (optional — TCG emulation works without it, just slower)
  • Python 3.11+ managed with uv

Install

# From this checkout
uv sync

# Add to Claude Code
claude mcp add mcqemu -- uv run --directory /path/to/mcqemu mcqemu

What it can do

Group Tools
Lifecycle launch_vm, stop_vm, pause_vm, resume_vm, attach_vm, forget_vm
Sandboxes sandbox_vm (overlay + launch + wait-for-agent in one call), sandbox_destroy
Inspect list_vms, vm_info
Live snapshots vm_snapshot_create / restore / delete / list
See & drive vm_screenshot (PNG), vm_send_keys, vm_type_text, vm_click, vm_mouse_move (relative PS/2, for guests without tablet drivers), vm_serial_read
Disk images image_create, image_info, image_convert, image_resize, image_snapshot_*
Guest agent guest_ping, guest_info, guest_exec, guest_file_read, guest_file_write

VMs are daemonized QEMU processes with QMP control sockets, so they survive MCP server restarts. The registry lives in ~/.local/share/mcqemu/, sockets in $XDG_RUNTIME_DIR/mcqemu/.

Guest tools (guest_*) need qemu-guest-agent installed inside the guest OS; the host-side virtio-serial channel is wired on every launch, so installing the agent in the guest is the only step.

Port forwards accept "2222:22" (explicit, collision-checked up front), "auto:22", or just "22" — auto forms pick a free host port and the launch result reports what was chosen.

Quick start

Disposable sandbox from any base image with qemu-guest-agent inside:

sandbox_vm(base_image="~/vms/ubuntu-agent.qcow2")
# -> overlay created, VM booted, agent waited for, free port forwarded to 22
guest_exec(name="sandbox", command="uname", args=["-a"])
sandbox_destroy(name="sandbox")   # stops VM, deletes overlay; base untouched

Installing an OS from scratch:

image_create(path="~/vms/test.qcow2", size="10G")
launch_vm(name="test", disks=["~/vms/test.qcow2"], iso="~/isos/alpine.iso",
          port_forwards=["auto:22"])
# ... drive the installer with vm_screenshot / vm_type_text / vm_send_keys ...
stop_vm(name="test")
launch_vm(name="test", disks=["~/vms/test.qcow2"])
guest_exec(name="test", command="uname", args=["-a"])

Development

uv run pytest                  # unit tests (QMP and subprocess mocked)
uv run pytest -m integration   # acceptance: every tool group against real QEMU
uv run ruff check .

The acceptance suite boots real VMs. The guest-agent and snapshot journey needs a base image with qemu-guest-agent installed — it looks for ~/vms/ubuntu-agent.qcow2, overridable with MCQEMU_TEST_BASE_IMAGE, and skips cleanly when absent.

Description
MCP server for managing QEMU virtual machines: lifecycle, disposable sandboxes, live snapshots, guest agent, and see-and-drive screenshots/input
Readme MIT 4.7 MiB
Languages
Python 57.5%
MDX 36.2%
CSS 2.2%
Astro 1.9%
JavaScript 0.9%
Other 1.3%