Blame SOURCES/kvm-block-Fix-copy-on-read-crash-with-partial-final-clus.patch

357786
From aa04dc32326b3c03f0af75dd9a87530691cd53bf Mon Sep 17 00:00:00 2001
357786
From: Kevin Wolf <kwolf@redhat.com>
357786
Date: Thu, 12 Jul 2018 15:00:08 +0200
357786
Subject: [PATCH 40/89] block: Fix copy-on-read crash with partial final
357786
 cluster
357786
357786
RH-Author: Kevin Wolf <kwolf@redhat.com>
357786
Message-id: <20180712150008.23662-2-kwolf@redhat.com>
357786
Patchwork-id: 81331
357786
O-Subject: [RHV-7.6 qemu-kvm-rhev PATCH 1/1] block: Fix copy-on-read crash with partial final cluster
357786
Bugzilla: 1590640
357786
RH-Acked-by: Max Reitz <mreitz@redhat.com>
357786
RH-Acked-by: Fam Zheng <famz@redhat.com>
357786
RH-Acked-by: John Snow <jsnow@redhat.com>
357786
RH-Acked-by: Richard Jones <rjones@redhat.com>
357786
357786
If the virtual disk size isn't aligned to full clusters,
357786
bdrv_co_do_copy_on_readv() may get pnum == 0 before having the full
357786
cluster completed, which will let it run into an assertion failure:
357786
357786
qemu-io: block/io.c:1203: bdrv_co_do_copy_on_readv: Assertion `skip_bytes < pnum' failed.
357786
357786
Check for EOF, assert that we read at least as much as the read request
357786
originally wanted to have (which is true at EOF because otherwise
357786
bdrv_check_byte_request() would already have returned an error) and
357786
return success early even though we couldn't copy the full cluster.
357786
357786
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
357786
(cherry picked from commit b0ddcbbb36a66a605eb232b905cb49b1cc72e74e)
357786
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
357786
Signed-off-by: Miroslav Rezanina <mrezanin@redhat.com>
357786
---
357786
 block/io.c                 | 6 ++++++
357786
 tests/qemu-iotests/197     | 9 +++++++++
357786
 tests/qemu-iotests/197.out | 8 ++++++++
357786
 3 files changed, 23 insertions(+)
357786
357786
diff --git a/block/io.c b/block/io.c
357786
index ad8afc0..ac36d1c 100644
357786
--- a/block/io.c
357786
+++ b/block/io.c
357786
@@ -1095,6 +1095,12 @@ static int coroutine_fn bdrv_co_do_copy_on_readv(BdrvChild *child,
357786
             pnum = MIN(cluster_bytes, max_transfer);
357786
         }
357786
 
357786
+        /* Stop at EOF if the image ends in the middle of the cluster */
357786
+        if (ret == 0 && pnum == 0) {
357786
+            assert(progress >= bytes);
357786
+            break;
357786
+        }
357786
+
357786
         assert(skip_bytes < pnum);
357786
 
357786
         if (ret <= 0) {
357786
diff --git a/tests/qemu-iotests/197 b/tests/qemu-iotests/197
357786
index 3ae4975..0369aa5 100755
357786
--- a/tests/qemu-iotests/197
357786
+++ b/tests/qemu-iotests/197
357786
@@ -109,6 +109,15 @@ $QEMU_IO -f qcow2 -c map "$TEST_WRAP"
357786
 _check_test_img
357786
 $QEMU_IMG compare -f $IMGFMT -F qcow2 "$TEST_IMG" "$TEST_WRAP"
357786
 
357786
+echo
357786
+echo '=== Partial final cluster ==='
357786
+echo
357786
+
357786
+_make_test_img 1024
357786
+$QEMU_IO -f $IMGFMT -C -c 'read 0 1024' "$TEST_IMG" | _filter_qemu_io
357786
+$QEMU_IO -f $IMGFMT -c map "$TEST_IMG"
357786
+_check_test_img
357786
+
357786
 # success, all done
357786
 echo '*** done'
357786
 status=0
357786
diff --git a/tests/qemu-iotests/197.out b/tests/qemu-iotests/197.out
357786
index 52b4137..8febda5 100644
357786
--- a/tests/qemu-iotests/197.out
357786
+++ b/tests/qemu-iotests/197.out
357786
@@ -23,4 +23,12 @@ can't open device TEST_DIR/t.wrap.qcow2: Can't use copy-on-read on read-only dev
357786
 1023.938 MiB (0x3fff0000) bytes not allocated at offset 3 GiB (0xc0010000)
357786
 No errors were found on the image.
357786
 Images are identical.
357786
+
357786
+=== Partial final cluster ===
357786
+
357786
+Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=1024
357786
+read 1024/1024 bytes at offset 0
357786
+1 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
357786
+1 KiB (0x400) bytes     allocated at offset 0 bytes (0x0)
357786
+No errors were found on the image.
357786
 *** done
357786
-- 
357786
1.8.3.1
357786