Docs / Introduction

MicroVMs

Container workloads with a real kernel boundary: how microVMs differ from VMs, why HosterOS removed the setup they used to need, and how to run a compose stack inside one.

A microVM is a virtual machine with its own kernel that boots in a fraction of the time a full QEMU guest takes, run on Cloud Hypervisor instead of QEMU. You put a compose.yaml in it and it runs your containers — with a hypervisor boundary underneath instead of a shared kernel.

That is the whole point. Containers share a kernel, which is fine until it is not, and “not” usually means a tenant boundary, an untrusted image, or a compliance question you would rather answer with a hard edge than with a namespace.

There is no setup

This used to be an afternoon of host preparation: install Cloud Hypervisor, install virtiofsd, sort out EFI firmware, possibly build a direct-boot kernel, then create a container dataset and seed a template into it by hand.

HosterOS does all of it. The virtualisation stack — QEMU and Cloud Hypervisor — is installed into the system image when the ISO is built, so it lands on the machine offline, during the install. The encrypted and unencrypted container datasets are part of the standard dataset hierarchy the installer creates. Firmware boot is the default and needs nothing from you.

If you find a guide telling you to install a hypervisor before you can use microVMs, it predates HosterOS.

The lifecycle is the one you already know

hoster microvm mirrors hoster vm, deliberately. Same verbs, same shape, same retention rules:

hoster microvm template pull debian13
hoster microvm deploy --name demo-app
hoster microvm list
hoster microvm status demo-app
hoster microvm console demo-app
hoster microvm stop demo-app
hoster microvm destroy demo-app

Templates, snapshots, replication and disaster-recovery backups are there too — hoster microvm template pull, snapshot create, replicate, dr-backup — and behave the way their VM counterparts do. Choosing between a VM and a microVM is a workload decision, not a second platform to learn.

Screenshot

Take a screenshot of `hoster microvm list` next to `hoster vm list` on the same host, to show the two guest types managed side by side.

First, pull a template

MicroVMs clone from templates exactly the way VMs do, and they have their own catalogue and their own set of commands. A template has to be on the node before anything can be deployed from it — including debian13, which is only the default name, not something that arrives with the install.

hoster microvm template list-online     # what the repository publishes
hoster microvm template pull debian13   # bring it down into a container dataset
hoster microvm template list            # what this node already has
Flag on pull What it does
--parent-dataset Which container dataset to put it in
--link-only Print only the download URL, for fetching through your own mirror
--force Re-download even when the local copy is already up to date

The Downloads page lists the same microVM catalogue with direct archive links, alongside the VM images. To build one of your own, see Building your own template.

Keeping templates in step

Two more commands matter once there is more than one dataset or more than one node:

hoster microvm template sync --check        # between container datasets on this host
hoster microvm template replicate --check   # from cluster peers to this host

Both take --check to show what they would do without doing it. In a cluster the scheduler runs the replication for you on a schedule, so a node is not missing the template you are about to deploy from; these are the manual equivalents.

Deploying one

hoster microvm deploy --name demo-app --compose-file ./compose.yaml

--template defaults to debian13 — the one pulled above — and --compose-file copies your compose file straight into the guest’s /data/compose.yaml as it is built, so once the template is local a deploy is the only command you run.

Flag Default Notes
--template debian13 Container-dataset template to clone
--compose-file Copied to /data/compose.yaml in the new guest
--cpus 2
--ram 2G
--os-disk-size 30G Absolute size for disk0.img
--disk-expand Grow the cloned disk by an amount instead, e.g. 20G
--parent-dataset first container dataset Which container dataset to build in
--bridge the internal bridge
--boot-mode firmware kernel switches to direct-kernel boot
--host-device PCI device to pass through, by BDF or sysfs path

The two deploy commands do not name their flags the same way. A VM takes --os-template (with --template as an alias), --cpu-cores, --cpu-sockets and --cpu-threads; a microVM takes --template and a single --cpus. The same is true of template pull: the VM version has a --debug flag that prints the shell commands instead of running them, and the microVM version does not. Worth knowing before you copy a command from one page to the other.

Firmware boot, or direct kernel

firmware is the default and is what you want. --boot-mode kernel boots a kernel image directly — faster still, at the cost of caring about the image and its command line, which default to /opt/hoster/firmware/vmlinux.bin and console=ttyS0 root=/dev/vda1 rw. Reach for it when boot latency is the thing you are optimising, not before.

Where your workload lives

Deploying demo-app clones the template into a container dataset and creates a directory on the host, which is mounted inside the guest as /data:

Output
<container dataset mountpoint>/demo-app/data   →   /data

Before start, the guest looks for a compose file at one of:

Output
/data/docker-compose.yml
/data/docker-compose.yaml
/data/compose.yaml

The raw disk holds the guest OS and the Docker daemon’s own storage. /data is for the compose file and your application’s data — which means the thing you care about keeping is on the host side of a mount, where you can see it, back it up, and hand it to a different guest.

Screenshot

Take a screenshot of a microVM's /data directory on the host next to `hoster microvm status` for the same guest, showing the compose file and the running state together.

Extra mounts

hoster microvm mount add demo-app ...
hoster microvm mount update demo-app ...
hoster microvm mount remove demo-app ...

Mounts come in two kinds: internal, for paths that live inside the container dataset alongside the guest, and external, for paths elsewhere on the host — a LeilFS path, a bulk data volume, anything the workload needs but should not own.

PCI passthrough

hoster microvm pci list demo-app
hoster microvm pci add demo-app <device>
hoster microvm pci remove demo-app <device>

Devices have to be reserved for guests before any of this — bound to vfio-pci at boot rather than claimed by the host. The installer does that if you selected them on screen 9, which also explains why selecting a GPU pulls in its audio function, and covers the laptop and mini-PC case where a discrete GPU shares an IOMMU group with a non-ACS root port.

Do that at install time where you can. It means the bindings are in the initramfs from first boot and the host never briefly claims the device on its way up.

When to use which

Virtual machine MicroVM
Hypervisor QEMU Cloud Hypervisor
Boots in seconds a fraction of that
Workload an operating system you administer containers, from a compose file
Isolation its own kernel its own kernel
Managed by hoster vm hoster microvm

Both give you a kernel boundary. Choose a microVM when the unit of work is a compose stack and you want it to start quickly; choose a VM when the unit of work is a machine.

Next

Something unclear on this page?

Ask about this specific page and we will come back to you. Your question arrives with a link to it, so you do not have to describe where you were.