|
|
9ae3a8 |
From ebd7d27935a5ec9d5c72403fc1cd60af2e450e7c Mon Sep 17 00:00:00 2001
|
|
|
9ae3a8 |
From: Paolo Bonzini <pbonzini@redhat.com>
|
|
|
9ae3a8 |
Date: Fri, 18 Oct 2013 08:14:33 +0200
|
|
|
9ae3a8 |
Subject: [PATCH 08/81] block: expect errors from bdrv_co_is_allocated
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
RH-Author: Paolo Bonzini <pbonzini@redhat.com>
|
|
|
9ae3a8 |
Message-id: <1382084091-16636-9-git-send-email-pbonzini@redhat.com>
|
|
|
9ae3a8 |
Patchwork-id: 54992
|
|
|
9ae3a8 |
O-Subject: [RHEL 7.0 qemu-kvm PATCH 08/26] block: expect errors from bdrv_co_is_allocated
|
|
|
9ae3a8 |
Bugzilla: 989646
|
|
|
9ae3a8 |
RH-Acked-by: Stefan Hajnoczi <stefanha@redhat.com>
|
|
|
9ae3a8 |
RH-Acked-by: Max Reitz <mreitz@redhat.com>
|
|
|
9ae3a8 |
RH-Acked-by: Kevin Wolf <kwolf@redhat.com>
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
Some bdrv_is_allocated callers do not expect errors, but the fallback
|
|
|
9ae3a8 |
in qcow2.c might make other callers trip on assertion failures or
|
|
|
9ae3a8 |
infinite loops.
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
Fix the callers to always look for errors.
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
Cc: qemu-stable@nongnu.org
|
|
|
9ae3a8 |
Reviewed-by: Eric Blake <eblake@redhat.com>
|
|
|
9ae3a8 |
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
|
|
|
9ae3a8 |
(cherry picked from commit d663640c04f2aab810915c556390211d75457704)
|
|
|
9ae3a8 |
---
|
|
|
9ae3a8 |
block.c | 7 +++++--
|
|
|
9ae3a8 |
block/cow.c | 6 +++++-
|
|
|
9ae3a8 |
block/qcow2.c | 4 +---
|
|
|
9ae3a8 |
block/stream.c | 2 +-
|
|
|
9ae3a8 |
qemu-img.c | 16 ++++++++++++++--
|
|
|
9ae3a8 |
qemu-io.c | 4 ++++
|
|
|
9ae3a8 |
6 files changed, 30 insertions(+), 9 deletions(-)
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
Signed-off-by: Miroslav Rezanina <mrezanin@redhat.com>
|
|
|
9ae3a8 |
---
|
|
|
9ae3a8 |
block.c | 7 +++++--
|
|
|
9ae3a8 |
block/cow.c | 6 +++++-
|
|
|
9ae3a8 |
block/qcow2.c | 4 +---
|
|
|
9ae3a8 |
block/stream.c | 2 +-
|
|
|
9ae3a8 |
qemu-img.c | 16 ++++++++++++++--
|
|
|
9ae3a8 |
qemu-io.c | 4 ++++
|
|
|
9ae3a8 |
6 files changed, 30 insertions(+), 9 deletions(-)
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
diff --git a/block.c b/block.c
|
|
|
9ae3a8 |
index 46d9420..d838a3c 100644
|
|
|
9ae3a8 |
--- a/block.c
|
|
|
9ae3a8 |
+++ b/block.c
|
|
|
9ae3a8 |
@@ -1815,8 +1815,11 @@ int bdrv_commit(BlockDriverState *bs)
|
|
|
9ae3a8 |
buf = g_malloc(COMMIT_BUF_SECTORS * BDRV_SECTOR_SIZE);
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
for (sector = 0; sector < total_sectors; sector += n) {
|
|
|
9ae3a8 |
- if (bdrv_is_allocated(bs, sector, COMMIT_BUF_SECTORS, &n)) {
|
|
|
9ae3a8 |
-
|
|
|
9ae3a8 |
+ ret = bdrv_is_allocated(bs, sector, COMMIT_BUF_SECTORS, &n);
|
|
|
9ae3a8 |
+ if (ret < 0) {
|
|
|
9ae3a8 |
+ goto ro_cleanup;
|
|
|
9ae3a8 |
+ }
|
|
|
9ae3a8 |
+ if (ret) {
|
|
|
9ae3a8 |
if (bdrv_read(bs, sector, buf, n) != 0) {
|
|
|
9ae3a8 |
ret = -EIO;
|
|
|
9ae3a8 |
goto ro_cleanup;
|
|
|
9ae3a8 |
diff --git a/block/cow.c b/block/cow.c
|
|
|
9ae3a8 |
index 21bceaa..5a33b46 100644
|
|
|
9ae3a8 |
--- a/block/cow.c
|
|
|
9ae3a8 |
+++ b/block/cow.c
|
|
|
9ae3a8 |
@@ -212,7 +212,11 @@ static int coroutine_fn cow_read(BlockDriverState *bs, int64_t sector_num,
|
|
|
9ae3a8 |
int ret, n;
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
while (nb_sectors > 0) {
|
|
|
9ae3a8 |
- if (cow_co_is_allocated(bs, sector_num, nb_sectors, &n)) {
|
|
|
9ae3a8 |
+ ret = cow_co_is_allocated(bs, sector_num, nb_sectors, &n);
|
|
|
9ae3a8 |
+ if (ret < 0) {
|
|
|
9ae3a8 |
+ return ret;
|
|
|
9ae3a8 |
+ }
|
|
|
9ae3a8 |
+ if (ret) {
|
|
|
9ae3a8 |
ret = bdrv_pread(bs->file,
|
|
|
9ae3a8 |
s->cow_sectors_offset + sector_num * 512,
|
|
|
9ae3a8 |
buf, n * 512);
|
|
|
9ae3a8 |
diff --git a/block/qcow2.c b/block/qcow2.c
|
|
|
9ae3a8 |
index 70da5bd..f6e64d2 100644
|
|
|
9ae3a8 |
--- a/block/qcow2.c
|
|
|
9ae3a8 |
+++ b/block/qcow2.c
|
|
|
9ae3a8 |
@@ -648,13 +648,11 @@ static int coroutine_fn qcow2_co_is_allocated(BlockDriverState *bs,
|
|
|
9ae3a8 |
int ret;
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
*pnum = nb_sectors;
|
|
|
9ae3a8 |
- /* FIXME We can get errors here, but the bdrv_co_is_allocated interface
|
|
|
9ae3a8 |
- * can't pass them on today */
|
|
|
9ae3a8 |
qemu_co_mutex_lock(&s->lock);
|
|
|
9ae3a8 |
ret = qcow2_get_cluster_offset(bs, sector_num << 9, pnum, &cluster_offset);
|
|
|
9ae3a8 |
qemu_co_mutex_unlock(&s->lock);
|
|
|
9ae3a8 |
if (ret < 0) {
|
|
|
9ae3a8 |
- *pnum = 0;
|
|
|
9ae3a8 |
+ return ret;
|
|
|
9ae3a8 |
}
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
return (cluster_offset != 0) || (ret == QCOW2_CLUSTER_ZERO);
|
|
|
9ae3a8 |
diff --git a/block/stream.c b/block/stream.c
|
|
|
9ae3a8 |
index 9674c31..995b97b 100644
|
|
|
9ae3a8 |
--- a/block/stream.c
|
|
|
9ae3a8 |
+++ b/block/stream.c
|
|
|
9ae3a8 |
@@ -120,7 +120,7 @@ wait:
|
|
|
9ae3a8 |
if (ret == 1) {
|
|
|
9ae3a8 |
/* Allocated in the top, no need to copy. */
|
|
|
9ae3a8 |
copy = false;
|
|
|
9ae3a8 |
- } else {
|
|
|
9ae3a8 |
+ } else if (ret >= 0) {
|
|
|
9ae3a8 |
/* Copy if allocated in the intermediate images. Limit to the
|
|
|
9ae3a8 |
* known-unallocated area [sector_num, sector_num+n). */
|
|
|
9ae3a8 |
ret = bdrv_is_allocated_above(bs->backing_hd, base,
|
|
|
9ae3a8 |
diff --git a/qemu-img.c b/qemu-img.c
|
|
|
9ae3a8 |
index 3b11414..28efb4f 100644
|
|
|
9ae3a8 |
--- a/qemu-img.c
|
|
|
9ae3a8 |
+++ b/qemu-img.c
|
|
|
9ae3a8 |
@@ -1482,8 +1482,15 @@ static int img_convert(int argc, char **argv)
|
|
|
9ae3a8 |
are present in both the output's and input's base images (no
|
|
|
9ae3a8 |
need to copy them). */
|
|
|
9ae3a8 |
if (out_baseimg) {
|
|
|
9ae3a8 |
- if (!bdrv_is_allocated(bs[bs_i], sector_num - bs_offset,
|
|
|
9ae3a8 |
- n, &n1)) {
|
|
|
9ae3a8 |
+ ret = bdrv_is_allocated(bs[bs_i], sector_num - bs_offset,
|
|
|
9ae3a8 |
+ n, &n1;;
|
|
|
9ae3a8 |
+ if (ret < 0) {
|
|
|
9ae3a8 |
+ error_report("error while reading metadata for sector "
|
|
|
9ae3a8 |
+ "%" PRId64 ": %s",
|
|
|
9ae3a8 |
+ sector_num - bs_offset, strerror(-ret));
|
|
|
9ae3a8 |
+ goto out;
|
|
|
9ae3a8 |
+ }
|
|
|
9ae3a8 |
+ if (!ret) {
|
|
|
9ae3a8 |
sector_num += n1;
|
|
|
9ae3a8 |
continue;
|
|
|
9ae3a8 |
}
|
|
|
9ae3a8 |
@@ -2217,6 +2224,11 @@ static int img_rebase(int argc, char **argv)
|
|
|
9ae3a8 |
|
|
|
9ae3a8 |
/* If the cluster is allocated, we don't need to take action */
|
|
|
9ae3a8 |
ret = bdrv_is_allocated(bs, sector, n, &n);
|
|
|
9ae3a8 |
+ if (ret < 0) {
|
|
|
9ae3a8 |
+ error_report("error while reading image metadata: %s",
|
|
|
9ae3a8 |
+ strerror(-ret));
|
|
|
9ae3a8 |
+ goto out;
|
|
|
9ae3a8 |
+ }
|
|
|
9ae3a8 |
if (ret) {
|
|
|
9ae3a8 |
continue;
|
|
|
9ae3a8 |
}
|
|
|
9ae3a8 |
diff --git a/qemu-io.c b/qemu-io.c
|
|
|
9ae3a8 |
index 5045ff8..bdcce7f 100644
|
|
|
9ae3a8 |
--- a/qemu-io.c
|
|
|
9ae3a8 |
+++ b/qemu-io.c
|
|
|
9ae3a8 |
@@ -1607,6 +1607,10 @@ static int alloc_f(int argc, char **argv)
|
|
|
9ae3a8 |
sector_num = offset >> 9;
|
|
|
9ae3a8 |
while (remaining) {
|
|
|
9ae3a8 |
ret = bdrv_is_allocated(bs, sector_num, remaining, &num);
|
|
|
9ae3a8 |
+ if (ret < 0) {
|
|
|
9ae3a8 |
+ printf("is_allocated failed: %s\n", strerror(-ret));
|
|
|
9ae3a8 |
+ return 0;
|
|
|
9ae3a8 |
+ }
|
|
|
9ae3a8 |
sector_num += num;
|
|
|
9ae3a8 |
remaining -= num;
|
|
|
9ae3a8 |
if (ret) {
|
|
|
9ae3a8 |
--
|
|
|
9ae3a8 |
1.7.1
|
|
|
9ae3a8 |
|