Loading...
Back to Comparisons

UPDATED 2026-07-26

Comparison Guide

Firecracker vs gVisor vs Containers for Agent Sandboxing (2026)

Choosing the isolation tier for untrusted agent-generated code: Firecracker microVMs (125 ms boots, <5 MiB overhead) vs gVisor's userspace kernel vs hardened containers - with the runc escape CVEs, gVisor's own published throughput numbers, and the map of which sandbox products run on what.

Audience: Platform and security engineers choosing an isolation boundary for code that AI agents write and execute - code no human reviewed before it runsUse case: Picking the sandboxing tier for agent code execution: hardware-virtualized microVMs vs a userspace kernel vs plain hardened containers, trading blast radius against cold-start latency, compatibility, GPU access, and ops cost2026-07-26

Verdict

Treat this as a trust-tier decision, not a benchmark contest. If your sandbox runs fully untrusted code - arbitrary strangers' prompts producing arbitrary programs - Firecracker's hardware virtualization boundary is the defensible default: the NSDI 2020 paper and AWS's own launch materials document boots to application code in as little as 125 ms, under 5 MiB memory overhead per microVM, and up to 150 microVM creations per second per host, which is why AWS Lambda, Fly.io Machines, E2B, and Vercel Sandbox all sit on it. Choose gVisor when you need stronger-than-container isolation with container-grade operations - runsc is a drop-in OCI runtime - or when you need GPUs inside the sandbox, which Firecracker simply does not offer and gVisor's nvproxy does (the reason Modal runs on gVisor). And do not pay for either tier reflexively: for semi-trusted code your own team wrote where the agent merely chooses which vetted tool to invoke, a hardened container with seccomp, no-new-privileges, read-only rootfs, and dropped capabilities is cheaper, faster, and fully compatible - plain containers win that row outright. The runc escapes (CVE-2019-5736, CVE-2024-21626) are the reason 'just use Docker' is not an answer for genuinely untrusted code: both let a malicious container reach the host.

The three options draw their security boundary in different places, and the numbers are all public. Firecracker is a KVM-based virtual machine monitor with a minimal device model; its USENIX NSDI 2020 paper ('Firecracker: Lightweight Virtualization for Serverless Applications', Agache et al.) documents boots to application code in as little as 125 ms, <5 MiB per-microVM overhead, 150 microVMs/second/host creation rate, and thousands of microVMs per host - figures AWS repeats in its launch blog (aws.amazon.com). gVisor takes a different bet: the Sentry, a userspace kernel written in Go, implements the Linux syscall ABI and intercepts the workload's syscalls (via the Systrap platform, built on seccomp-bpf, or KVM), so the host kernel's attack surface shrinks without hardware virtualization. The cost is compatibility and I/O: gVisor implements a large subset - not all - of Linux syscalls (the USENIX HotCloud '19 gVisor case study counted 211 implemented against 108 unsupported), and gVisor's own engineering blog benchmarked its userspace network stack at roughly 17 Gbps download vs 42 Gbps native and 8 Gbps upload vs 43 Gbps native (gvisor.dev, 2020 networking-security post). Plain containers share the host kernel outright - full compatibility, near-zero overhead, and a blast radius defined by the next runtime escape: runc CVE-2019-5736 let a malicious container overwrite the host runc binary and gain root on the host, and runc CVE-2024-21626 (January 2024) let a container escape via a leaked file-descriptor working directory. Production adoption maps cleanly onto these tradeoffs: Firecracker under AWS Lambda and Fargate, Fly.io Machines, E2B, and Vercel Sandbox; gVisor under Google Cloud Run's first-generation execution environment, GKE Sandbox, App Engine, and Modal (Cloud Run's second-generation environment, the default for new services, moved to microVM-based isolation - Google itself climbing the same trust ladder).

Decision Table

Firecracker (KVM-based microVMs with a minimal device model)gVisor (userspace application kernel intercepting syscalls)
CriterionEdgeExplanation
Isolation boundary and blast radiusFirecracker (KVM-based microVMs with a minimal device model) Best edgeFirecracker's boundary is hardware virtualization: the guest runs its own Linux kernel behind KVM, and an attacker who owns the guest kernel still faces the VMM and the hardware virtualization layer, with Firecracker's minimal device model (no PCI passthrough, a handful of virtio devices) keeping the escape surface small - the design argument of the NSDI 2020 paper. gVisor's Sentry intercepts syscalls in userspace and forwards only a reduced set to the host (analyses of its seccomp policy count around 55 host syscalls allowed), which is a real hardening step - but the Sentry still runs on the shared host kernel, so a kernel bug reachable through that reduced set is still a host compromise. For maximum-distrust workloads, the hardware boundary wins.
Cold-start latency and densityTieThis is the row plain containers win outright: namespace creation is effectively free, adds no guest kernel, and no VMM - nothing else matches fork-and-exec economics. Between the two sandboxes it is closer than the 'VMs are slow' instinct suggests: Firecracker documents boots as fast as 125 ms, <5 MiB overhead, and 150 microVMs/second/host (NSDI 2020), which is why per-request microVMs are viable at Lambda scale; gVisor containers also start in tens to hundreds of milliseconds since there is no guest kernel to boot, though every syscall thereafter pays the interception tax. If raw start latency and density dominate and the code is not truly hostile, drop a tier and harden a container.
Application compatibilityFirecracker (KVM-based microVMs with a minimal device model) Best edgeFirecracker runs a real Linux kernel in the guest, so anything that runs on that kernel runs in the sandbox - the compatibility question moves to 'which kernel and rootfs did you build', not 'which syscalls are missing'. gVisor reimplements the Linux ABI in the Sentry and its docs are explicit that coverage is a subset: historically around 211 syscalls implemented with over a hundred unsupported, plus known gaps in /proc surfaces and kernel-coupled edge cases. Agent-generated code is adversarially weird by nature - it will find the unimplemented syscall. Budget a compatibility test pass over your actual workload before committing to gVisor.
Operational integration (OCI, Docker, Kubernetes)gVisor (userspace application kernel intercepting syscalls) Best edgegVisor ships runsc, an OCI-compatible runtime: one runtime entry in Docker's daemon.json or a Kubernetes RuntimeClass and your existing images, registries, and orchestration keep working - this is exactly how GKE Sandbox packages it. Firecracker has no native OCI story: you assemble guest kernels, rootfs images, jailer configuration, and networking yourself, or adopt an integration layer like Kata Containers or firecracker-containerd and inherit its complexity. For a small team without a platform group, gVisor's drop-in path is the difference between an afternoon and a quarter.
I/O and network throughputFirecracker (KVM-based microVMs with a minimal device model) Best edgegVisor's published numbers are the honest datapoint here, and they come from gVisor's own blog: its userspace netstack measured roughly 17 Gbps download against 42 Gbps for native Linux and 8 Gbps upload against 43 Gbps (gvisor.dev networking-security post) - better than its 2019 baseline but still a large gap on network-heavy paths, and secondary benchmarking consistently finds gVisor's overhead concentrated in syscall- and I/O-heavy workloads while CPU-bound code runs near native. Firecracker's virtio devices carry their own tax versus bare metal but sit closer to native for bulk I/O. If your agents mostly do CPU-bound computation, this row barely matters; if they shovel data, it does.
GPU access inside the sandboxgVisor (userspace application kernel intercepting syscalls) Best edgeFirecracker's minimal device model deliberately excludes PCI passthrough, so GPU workloads are out of scope - a longstanding, documented position of the project. gVisor ships nvproxy, which proxies the NVIDIA driver interface into the sandbox, and Modal's platform is the production proof: gVisor-isolated containers running CUDA workloads. If your agent sandbox must run inference or CUDA code with real isolation, gVisor is the only one of these two that does it today; the alternative is full VMs (Kata with VFIO passthrough) at much higher cost.
Production adoption for agent-facing sandboxesTieBoth have flagship-scale deployments, so neither wins on 'who trusts it'. Firecracker underpins AWS Lambda and Fargate, Fly.io Machines, E2B's agent sandboxes, and Vercel Sandbox. gVisor underpins Google Cloud Run's first-generation execution environment, GKE Sandbox, App Engine, and Modal. The useful signal is the pattern in who chose what: products selling arbitrary-code execution to strangers picked Firecracker's hardware boundary; products optimizing developer ergonomics and GPU workloads on their own platform picked gVisor. Match your threat model to the cohort you belong to.

Choose Firecracker (KVM-based microVMs with a minimal device model) if...

  • Multi-tenant platforms executing arbitrary code from untrusted users - the Lambda/E2B/Vercel Sandbox threat model.
  • Teams that need per-execution ephemeral sandboxes at high churn: 150 microVMs/second/host creation and <5 MiB overhead make one-microVM-per-run economics work.
  • Workloads needing full Linux compatibility inside the sandbox (a real guest kernel, not a syscall-ABI subset).
  • Security postures that require a hardware virtualization boundary on paper - compliance regimes where 'userspace kernel' is a harder conversation than 'VM'.

Choose gVisor (userspace application kernel intercepting syscalls) if...

  • Teams that want meaningful isolation as a drop-in OCI runtime in existing Docker/Kubernetes infrastructure - one RuntimeClass, no kernel/rootfs/jailer engineering.
  • GPU-in-the-sandbox workloads: nvproxy is the only sandboxed GPU path in this comparison, proven at scale by Modal.
  • CPU-bound agent code (parsing, computation, API orchestration) where gVisor's syscall-interception overhead is negligible in practice.
  • Google-managed deployments: Cloud Run (first-gen execution environment), App Engine, and GKE Sandbox give you gVisor isolation without operating it yourself.

Decision rules

  • 01If the sandbox executes fully untrusted code - public users' prompts generating arbitrary programs - use Firecracker microVMs or a platform built on them (E2B, Fly.io Machines, Vercel Sandbox). The hardware virtualization boundary is the point; the NSDI-documented 125 ms boots mean you are not trading meaningful latency for it.
  • 02If you need stronger-than-container isolation with your existing Docker/Kubernetes workflow and team, use gVisor: runsc as an OCI runtime or GKE Sandbox gets you a reduced host-kernel attack surface without owning kernel images and jailers.
  • 03If agents need GPUs inside the sandbox, gVisor (nvproxy) is the only option on this page that provides it - Firecracker has no device passthrough. Modal is the production existence proof.
  • 04If the code is semi-trusted - your own agents invoking vetted tools, no arbitrary code synthesis - a hardened container (seccomp default profile, no-new-privileges, read-only rootfs, dropped capabilities, resource limits) is the right tier: full compatibility, fastest starts, zero new infrastructure.
  • 05Do not run genuinely untrusted code in plain containers because 'we have seccomp': runc CVE-2019-5736 and CVE-2024-21626 were both full container-to-host escapes in the default runtime path.
  • 06Before committing to gVisor, run your real agent workload through it: syscall coverage is a subset of Linux, and model-generated code reliably finds the gaps. Compatibility failures surface at runtime, not deploy time.
  • 07Measure I/O: gVisor's own blog puts its netstack at roughly 17/8 Gbps down/up against 42/43 native - fine for API-calling agents, painful for data-heavy pipelines.

Migration Notes

  • Container-to-gVisor is the cheap migration: same OCI images, add the runsc runtime, then fix whatever your compatibility test pass surfaces. Container-to-Firecracker is a re-platform: you now own guest kernels, rootfs builds, and VM networking, or you adopt Kata/firecracker-containerd as the bridge.
  • Design your execution API (submit code → get stdout/artifacts) as the stable seam. Products like E2B and Modal differ underneath precisely because the sandbox boundary hides the isolation tech - keep yours equally swappable so you can move tiers as your threat model hardens.
  • If you start on hardened containers, write down the trigger that forces the upgrade - e.g. 'we accept code generated from unauthenticated user input' - so the tier change is a planned migration, not an incident response after the next runc CVE.