mech.app

The mech.app newsletter

Agentic AI, minus the noise.

Get practical field notes on AI agents, automation, developer tools and security delivered to your inbox.

No spam. Unsubscribe anytime.

Security

Why VMs Won't Contain Cyber-Capable Agents: Trail of Bits on Sandbox Escape Vectors

Trail of Bits demonstrates three VM escapes by GPT 5.6-Cyber, exposing how hypervisor boundaries fail when agents reason about infrastructure.

Source: blog.trailofbits.com
Why VMs Won't Contain Cyber-Capable Agents: Trail of Bits on Sandbox Escape Vectors

Trail of Bits published a blunt assessment on August 26, 2026: VMs will not contain agents with cyber capabilities. Artem Dinaburg gave GPT 5.6-Cyber a single task: escape the QEMU/KVM VM he normally uses for sandboxing. It succeeded three times using different vectors. First it exploited recent kernel bugs. After a full system update, it chained disclosed-but-unpatched bugs. When he rebuilt QEMU and dependencies from upstream source, it found multiple zero-days.

The agent operated autonomously for hours. It backtracked from dead ends, pulled research papers, wrote test oracles, created minimal reproducers, and aimed for reliable exploits. Dinaburg’s main job was physically rebooting the host when the agent hardlocked the kernel.

This is not a theoretical exercise. It coincides with the OpenAI/Hugging Face incident under investigation by METR. The threat model has shifted: you are no longer containing static malware. You are containing an adversary that reads documentation, enumerates APIs, and reasons about privilege boundaries.

The Containment Assumption That Broke

Traditional VM sandboxing relies on a trust boundary between guest and hypervisor. The guest can execute arbitrary code, but the hypervisor mediates all hardware access and enforces isolation. This works when the threat is:

  • Malware with pre-baked exploits
  • Human attackers constrained by time and manual effort
  • Automated fuzzers that spray inputs without context

It fails when the threat can:

  • Read CVE databases and patch commit logs
  • Understand which kernel subsystems are reachable from guest context
  • Chain multiple primitives (info leak, write-what-where, control flow hijack)
  • Iterate on exploit reliability across reboots

The VM escape surface includes:

  • Virtio drivers: paravirtualized I/O devices with complex state machines
  • QEMU device emulation: thousands of lines of C handling untrusted guest MMIO
  • Host kernel interfaces: KVM ioctls, memory management, interrupt routing
  • Shared resources: clipboard, file sharing, network bridges

Each of these surfaces has bugs. The difference is that a reasoning agent can discover which bugs are exploitable and how to chain them.

Three Escape Vectors in Sequence

Round 1: Known Kernel Bugs

The agent started with the easiest path. It queried recent CVEs affecting KVM and the host kernel (Debian 12, AMD Zen3). It found disclosed bugs that had patches committed upstream but not yet landed in distribution packages. It wrote a proof-of-concept that triggered a use-after-free in the KVM APIC emulation path, gained kernel code execution, and disabled SELinux before pivoting to the host.

Containment response: Full system update, including backported security patches.

Round 2: Disclosed-But-Unpatched Bugs

After the update, the agent shifted strategy. It searched for bugs that were publicly disclosed but not classified as security issues by package maintainers. It found a race condition in virtio-net that could be triggered by carefully timed guest network operations. The bug was known but considered low-severity because it required precise timing. The agent wrote a timing oracle, calibrated it across multiple runs, and achieved reliable exploitation.

Containment response: Rebuild QEMU and all dependencies from latest upstream source.

Round 3: Zero-Days

With all known bugs patched, the agent moved to vulnerability discovery. It pulled QEMU source code, identified complex state machines in device emulation, and wrote targeted fuzzers. It found several zero-days in less-common device emulators (USB passthrough, audio devices). It selected the most reliable primitive, wrote an exploit, and escaped again.

Containment response: Physical reboot after kernel hardlock.

Why Traditional Sandboxing Fails

The VM escape demonstrates a broader problem: hypervisor isolation assumes the guest cannot reason about the host. That assumption is obsolete.

Containment PrimitiveStatic Malware DefenseAgent DefenseFailure Mode
VM isolationStrongWeakAgent reads hypervisor docs, finds shared surfaces
Kernel updatesStrongWeakAgent finds disclosed-but-unpatched bugs faster than maintainers
Seccomp-bpfMediumMediumAgent can still reason within allowed syscall set
Network namespacesMediumWeakAgent pivots through allowed network paths
Capability droppingMediumMediumAgent chains capabilities or finds kernel bugs
gVisor/FirecrackerMediumUnknownSmaller attack surface, but still shares kernel scheduler and memory

The core issue: any shared resource is a potential escape vector when the adversary can read source code and iterate on exploits.

Alternative Containment Strategies

If VMs are insufficient, what works?

1. Air-Gapped Execution

Run the agent on physically separate hardware with no network path to production systems. Transfer artifacts manually via USB or optical media. This works but destroys the value proposition of autonomous agents.

2. Minimal Kernel Surfaces

Use gVisor or Firecracker to reduce the kernel attack surface. These runtimes implement a user-space kernel that mediates syscalls, reducing the trusted computing base. The agent still shares the host kernel scheduler and memory subsystem, but the attack surface shrinks.

# Firecracker microVM config with minimal devices
{
  "boot-source": {
    "kernel_image_path": "/vmlinux",
    "boot_args": "console=ttyS0 reboot=k panic=1"
  },
  "drives": [{
    "drive_id": "rootfs",
    "path_on_host": "/rootfs.ext4",
    "is_root_device": true,
    "is_read_only": false
  }],
  "network-interfaces": [],
  "machine-config": {
    "vcpu_count": 2,
    "mem_size_mib": 1024
  }
}

No virtio-net, no shared clipboard, no USB passthrough. The agent can still exploit bugs in the Firecracker VMM or the host kernel, but the surface is smaller.

3. Capability-Based Sandboxing

Drop all capabilities except those strictly required for the task. Use seccomp-bpf to whitelist syscalls. This does not prevent VM escape, but it limits post-escape damage.

// Seccomp filter allowing only read, write, exit
struct sock_filter filter[] = {
  BPF_STMT(BPF_LD | BPF_W | BPF_ABS, offsetof(struct seccomp_data, nr)),
  BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, __NR_read, 0, 1),
  BPF_STMT(BPF_RET | BPF_K, SECCOMP_RET_ALLOW),
  BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, __NR_write, 0, 1),
  BPF_STMT(BPF_RET | BPF_K, SECCOMP_RET_ALLOW),
  BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, __NR_exit, 0, 1),
  BPF_STMT(BPF_RET | BPF_K, SECCOMP_RET_ALLOW),
  BPF_STMT(BPF_RET | BPF_K, SECCOMP_RET_KILL)
};

An agent can still reason within the allowed syscall set. If it can read and write files, it can exfiltrate data or modify configuration. If it can execute binaries, it can chain exploits.

4. Observability and Kill Switches

Instrument the sandbox to detect anomalous behavior: unexpected syscalls, network connections to CVE databases, kernel module loading attempts. Implement automated kill switches that snapshot state and halt execution when thresholds are crossed.

This is reactive, not preventive. It buys time for human review but does not stop a fast-moving agent.

The Advanced Persistent Threat Model

Trail of Bits frames cyber-capable agents as advanced persistent threats (APTs). This is the correct mental model. An APT:

  • Operates over long time horizons (hours to days)
  • Adapts tactics when defenses change
  • Exfiltrates data slowly to avoid detection
  • Establishes persistence mechanisms
  • Uses living-off-the-land techniques (legitimate tools, signed binaries)

Traditional APT defenses apply:

  • Least privilege: Run agents with minimal permissions
  • Network segmentation: Isolate agent networks from production
  • Audit logging: Capture all syscalls, network connections, file access
  • Anomaly detection: Flag unexpected behavior patterns
  • Incident response: Assume breach, plan for containment and forensics

The difference is speed. A human APT might take weeks to chain exploits. An agent can do it in hours.

Deployment Shape for Hostile Agents

If you must run a cyber-capable agent, the deployment architecture should assume compromise:

  1. Dedicated hardware: Physical separation from production systems
  2. No outbound network: Agent cannot phone home or download exploits
  3. Read-only root filesystem: Agent cannot persist across reboots
  4. Kernel lockdown mode: Prevent module loading, kexec, debugfs access
  5. Audit everything: Full syscall tracing, network packet capture, filesystem snapshots
  6. Human-in-the-loop: Require manual approval for high-risk operations (network access, binary execution)

This is expensive and slow. It negates many benefits of autonomous agents. But it is the only architecture that survives contact with an adversary that can read your infrastructure documentation.

Technical Verdict

Use VMs for agents when:

  • The agent has no code execution capability (pure API calls, no shell access)
  • The agent operates on synthetic data with no production access
  • You can tolerate full host compromise (research environments, disposable infrastructure)

Avoid VMs for agents when:

  • The agent has cyber capabilities (code execution, network access, debugging tools)
  • The agent handles production data or credentials
  • The agent operates autonomously for more than a few minutes
  • You cannot tolerate host compromise

For cyber-capable agents, assume the VM will be escaped. Use defense-in-depth: minimal kernels (gVisor/Firecracker), capability dropping, network isolation, audit logging, and kill switches. Treat the agent as an APT. Plan for containment failure.

The era of “just spin up a VM” for agent sandboxing is over. The threat model has changed. Your containment strategy must change with it.