An unaligned zero write causes NULL deferencing in bdrv_co_do_pwritev. That
path is reachable from bdrv_co_write_zeroes and bdrv_aio_write_zeroes.

You can easily trigger through the former with qemu-io, as the test case added
by 61815d6e0aa. For bdrv_aio_write_zeroes, in common cases there's always a
format driver (which uses 512 alignment), so it would be much rarer to have
unaligned requests (only concerning top level here, when the request goes down
to bs->file, where for example the alignment is 4k, it would then be calling
bdrv_co_write_zeroes because it's in a coroutine).

fc3959e4669a1c fixed bdrv_co_write_zeroes but not bdrv_aio_write_zeroes.  The
lattern is the actually used one by device model. Revert the previous fix, do
it in bdrv_co_do_pwritev, to cover both paths.

v6: Split the function to make it easier to reason. (Stefan)
    Add rev-by in 1, 3. (Stefan)

v5: Rebase on to the block/io.c split. (Kevin)

v4: "if (!qiov)" -> "if (!qiov && bytes >= align)". (Paolo)

v3: Fix the case where the unaligned request is contained within the first
    block. (Paolo)
    Also update iotests 033 to cover the code path with qemu-io.

v2: Split to three aligned pwritev.


Fam Zheng (3):
  Revert "block: Fix unaligned zero write"
  block: Fix NULL deference for unaligned write if qiov is NULL
  qemu-iotests: Test unaligned sub-block zero write

 block/io.c                 | 140 ++++++++++++++++++++++++++++++++-------------
 tests/qemu-iotests/033     |  13 +++++
 tests/qemu-iotests/033.out |  30 ++++++++++
 3 files changed, 144 insertions(+), 39 deletions(-)

-- 
2.1.0


Reply via email to