block/file-posix.c | 2 +- block/qcow2-cache.c | 8 + block/qcow2-refcount.c | 7 + block/qcow2.c | 1464 +++++++++++++++++++++- block/qcow2.h | 83 +- block/trace-events | 2 + docs/interop/qcow2.rst | 117 +- docs/system/qemu-block-drivers.rst.inc | 47 + hw/block/virtio-blk.c | 22 +- include/block/block_int-common.h | 15 +- qapi/block-core.json | 91 +- tests/qemu-iotests/tests/zoned-qcow2 | 209 +++ tests/qemu-iotests/tests/zoned-qcow2.out | 191 +++ 13 files changed, 2244 insertions(+), 14 deletions(-) create mode 100755 tests/qemu-iotests/tests/zoned-qcow2 create mode 100644 tests/qemu-iotests/tests/zoned-qcow2.out
This patch series add a new extension - zoned format - to the
qcow2 driver, allowing full zoned storage emulation on a qcow2
image file. A user can attach such an image to a guest and have
it appear as a host-managed zoned block device.
The zoned format is opt-in through a new qcow2 header extension
that pins the zone geometry. Behind the extension is a dedicated
zoned metadata region that stores one 8-byte write pointer (WP)
per zone. The extension is gated by an incompatible bit, so an
older qcow2 implementation cannot accidentally open the image.
Each write pointer is routed through the write pointer cache,
a Qcow2Cache object. The write pointer cache is written to disk
after the qcow2 metadata is written, thus guaranteeing that
the write pointer is updated after the corresponding data is
written.
Zone states are in memory. Read-only and offline states are
device-internal events, which are not modelled in qcow2
emulation for simplicity. The other zone states
(closed, empty, full) can be inferred from write poiner
values, presistent across QEMU reboots. The open states are
kept in memory using open zone lists.
To create a qcow2 file with the zoned format:
qemu-img create -f qcow2 zbc.qcow2 \
-o size=768M \
-o zone.size=64M \
-o zone.capacity=64M \
-o zone.conventional_zones=0 \
-o zone.max_append_bytes=4096 \
-o zone.max_open_zones=6 \
-o zone.max_active_zones=8 \
-o zone.mode=host-managed
Then attach it to a guest via the QEMU command line:
-blockdev node-name=drive1,driver=qcow2,\
file.driver=file,file.filename=zbc.qcow2 \
-device virtio-blk-pci,drive=drive1 \
v10->v11:
- add write ordering through write pointer cache [Stefan]
- add new test cases to iotests for zone append write
- add zoned image info to qemu-img --info
- move virtio-blk cross-zone-boundary merge fix into its own patch [Stefan]
- fix specs and docs:
* document bit 59 conventional-zone marker in qcow2.rst [Stefan]
* spell out write ordering for crash consistency [Stefan]
* QAPI: rephrase comments, bump version [Markus]
- fix review comments [Stefan]
v9->v10:
- add cross-boundary constraint for merging writes on zoned devices
- extract call from assert() to fix image creation crash
v8->v9:
- fix compilation err after modifying types
v7->v8:
- sets default values for zoned img confurations [Markus, Damien]
- changes the type of zone_size, zone_capacity from uint32_t to uint64_t [Stefan]
- fix docs [Stefan]
- modify append writes to increase concurrency [Damien, Stefan]
- use tailqueue to track active zones [Stefan]
- fix undefined behavior of ranges_overlap()
- fix the iotest of case 2(1)
v6->v7:
- modify zone resource managemant (style) [Damien]
- fix accessing list with negative index err
- add some tests for zrm in iotests
- address review comments [Markus]
v5->v6:
- fix docs and specs [Eric, Markus, Stefan]
- add general sanity checks for zoned device configurations while creation and opening [Eric]
- fix LRU when implicitly open a zone for a long time [Stefan]
v4->v5:
- add incompatible bit for zoned format [Eric]
- fix and manage zone resources via LRU [Damien]
- renaming functions and fields, spec changes [Markus, Damien]
- add closed zone list
- make qemu iotests for zoned device consecutive [Stefan]
v3->v4:
- use QLIST for implicit, explicit open zones management [Stefan]
- keep zone states in memory and drop state bits in wp metadata structure [Damien, Stefan]
- change zone resource management and iotests accordingly
- add tracing for number of implicit zones
- address review comments [Stefan, Markus]:
* documentation, config, style
v2->v3:
- drop zoned_profile option [Klaus]
- reformat doc comments of qcow2 [Markus]
- add input validation and checks for zoned information [Stefan]
- code style: format, comments, documentation, naming [Stefan]
- add tracing function for wp tracking [Stefan]
- reconstruct io path in check_zone_resources [Stefan]
v1->v2:
- add more tests to qemu-io zoned commands
- make zone append change state to full when wp reaches end
- add documentation to qcow2 zoned extension header
- address review comments (Stefan):
* fix zoned_mata allocation size
* use bitwise or than addition
* fix wp index overflow and locking
* cleanups: comments, naming
Sam Li (5):
docs/qcow2: add the zoned format feature
qcow2: add configurations for zoned format extension
virtio-blk: do not merge writes across a zone boundary
qcow2: add zoned emulation capability
iotests: test the zoned format feature for qcow2 file
block/file-posix.c | 2 +-
block/qcow2-cache.c | 8 +
block/qcow2-refcount.c | 7 +
block/qcow2.c | 1464 +++++++++++++++++++++-
block/qcow2.h | 83 +-
block/trace-events | 2 +
docs/interop/qcow2.rst | 117 +-
docs/system/qemu-block-drivers.rst.inc | 47 +
hw/block/virtio-blk.c | 22 +-
include/block/block_int-common.h | 15 +-
qapi/block-core.json | 91 +-
tests/qemu-iotests/tests/zoned-qcow2 | 209 +++
tests/qemu-iotests/tests/zoned-qcow2.out | 191 +++
13 files changed, 2244 insertions(+), 14 deletions(-)
create mode 100755 tests/qemu-iotests/tests/zoned-qcow2
create mode 100644 tests/qemu-iotests/tests/zoned-qcow2.out
--
2.53.0
On Mon, Jun 01, 2026 at 11:44:00PM +0200, Sam Li wrote: > This patch series add a new extension - zoned format - to the > qcow2 driver, allowing full zoned storage emulation on a qcow2 > image file. A user can attach such an image to a guest and have > it appear as a host-managed zoned block device. > > The zoned format is opt-in through a new qcow2 header extension > that pins the zone geometry. Behind the extension is a dedicated > zoned metadata region that stores one 8-byte write pointer (WP) > per zone. The extension is gated by an incompatible bit, so an > older qcow2 implementation cannot accidentally open the image. > > Each write pointer is routed through the write pointer cache, > a Qcow2Cache object. The write pointer cache is written to disk > after the qcow2 metadata is written, thus guaranteeing that > the write pointer is updated after the corresponding data is > written. > > Zone states are in memory. Read-only and offline states are > device-internal events, which are not modelled in qcow2 > emulation for simplicity. The other zone states > (closed, empty, full) can be inferred from write poiner > values, presistent across QEMU reboots. The open states are > kept in memory using open zone lists. > > To create a qcow2 file with the zoned format: > > qemu-img create -f qcow2 zbc.qcow2 \ > -o size=768M \ > -o zone.size=64M \ > -o zone.capacity=64M \ > -o zone.conventional_zones=0 \ > -o zone.max_append_bytes=4096 \ > -o zone.max_open_zones=6 \ > -o zone.max_active_zones=8 \ > -o zone.mode=host-managed > > Then attach it to a guest via the QEMU command line: > -blockdev node-name=drive1,driver=qcow2,\ > file.driver=file,file.filename=zbc.qcow2 \ > -device virtio-blk-pci,drive=drive1 \ Please run `make check-block-qcow` and ensure the tests pass. In some cases the test reference output may be outdated and you can simply copy the <test>.out.bad file over the <test>.out reference file. Thanks, Stefan
On Tue, Jun 2, 2026 at 10:06 PM Stefan Hajnoczi <stefanha@redhat.com> wrote: > > On Mon, Jun 01, 2026 at 11:44:00PM +0200, Sam Li wrote: > > This patch series add a new extension - zoned format - to the > > qcow2 driver, allowing full zoned storage emulation on a qcow2 > > image file. A user can attach such an image to a guest and have > > it appear as a host-managed zoned block device. > > > > The zoned format is opt-in through a new qcow2 header extension > > that pins the zone geometry. Behind the extension is a dedicated > > zoned metadata region that stores one 8-byte write pointer (WP) > > per zone. The extension is gated by an incompatible bit, so an > > older qcow2 implementation cannot accidentally open the image. > > > > Each write pointer is routed through the write pointer cache, > > a Qcow2Cache object. The write pointer cache is written to disk > > after the qcow2 metadata is written, thus guaranteeing that > > the write pointer is updated after the corresponding data is > > written. > > > > Zone states are in memory. Read-only and offline states are > > device-internal events, which are not modelled in qcow2 > > emulation for simplicity. The other zone states > > (closed, empty, full) can be inferred from write poiner > > values, presistent across QEMU reboots. The open states are > > kept in memory using open zone lists. > > > > To create a qcow2 file with the zoned format: > > > > qemu-img create -f qcow2 zbc.qcow2 \ > > -o size=768M \ > > -o zone.size=64M \ > > -o zone.capacity=64M \ > > -o zone.conventional_zones=0 \ > > -o zone.max_append_bytes=4096 \ > > -o zone.max_open_zones=6 \ > > -o zone.max_active_zones=8 \ > > -o zone.mode=host-managed > > > > Then attach it to a guest via the QEMU command line: > > -blockdev node-name=drive1,driver=qcow2,\ > > file.driver=file,file.filename=zbc.qcow2 \ > > -device virtio-blk-pci,drive=drive1 \ > > Please run `make check-block-qcow` and ensure the tests pass. In some > cases the test reference output may be outdated and you can simply copy > the <test>.out.bad file over the <test>.out reference file. Thanks, I will check this. Sam
On Tue, Jun 02, 2026 at 04:06:38PM -0400, Stefan Hajnoczi wrote: > On Mon, Jun 01, 2026 at 11:44:00PM +0200, Sam Li wrote: > > This patch series add a new extension - zoned format - to the > > qcow2 driver, allowing full zoned storage emulation on a qcow2 > > image file. A user can attach such an image to a guest and have > > it appear as a host-managed zoned block device. > > > > The zoned format is opt-in through a new qcow2 header extension > > that pins the zone geometry. Behind the extension is a dedicated > > zoned metadata region that stores one 8-byte write pointer (WP) > > per zone. The extension is gated by an incompatible bit, so an > > older qcow2 implementation cannot accidentally open the image. > > > > Each write pointer is routed through the write pointer cache, > > a Qcow2Cache object. The write pointer cache is written to disk > > after the qcow2 metadata is written, thus guaranteeing that > > the write pointer is updated after the corresponding data is > > written. > > > > Zone states are in memory. Read-only and offline states are > > device-internal events, which are not modelled in qcow2 > > emulation for simplicity. The other zone states > > (closed, empty, full) can be inferred from write poiner > > values, presistent across QEMU reboots. The open states are > > kept in memory using open zone lists. > > > > To create a qcow2 file with the zoned format: > > > > qemu-img create -f qcow2 zbc.qcow2 \ > > -o size=768M \ > > -o zone.size=64M \ > > -o zone.capacity=64M \ > > -o zone.conventional_zones=0 \ > > -o zone.max_append_bytes=4096 \ > > -o zone.max_open_zones=6 \ > > -o zone.max_active_zones=8 \ > > -o zone.mode=host-managed > > > > Then attach it to a guest via the QEMU command line: > > -blockdev node-name=drive1,driver=qcow2,\ > > file.driver=file,file.filename=zbc.qcow2 \ > > -device virtio-blk-pci,drive=drive1 \ > > Please run `make check-block-qcow` and ensure the tests pass. In some That should be `make check-block-qcow2`.
© 2016 - 2026 Red Hat, Inc.