From: Stefan Hajnoczi <stefanha@redhat.com>
To: qemu-devel@nongnu.org
Cc: Kevin Wolf <kwolf@redhat.com>,
Anthony Liguori <aliguori@us.ibm.com>,
Stefan Hajnoczi <stefanha@redhat.com>
Subject: [Qemu-devel] [PATCH 19/23] qcow2: Use byte granularity in qcow2_alloc_cluster_offset()
Date: Thu, 28 Mar 2013 17:40:33 +0100 [thread overview]
Message-ID: <1364488837-15916-20-git-send-email-stefanha@redhat.com> (raw)
In-Reply-To: <1364488837-15916-1-git-send-email-stefanha@redhat.com>
From: Kevin Wolf <kwolf@redhat.com>
This gets rid of the nb_clusters and keep_clusters and the associated
complicated calculations. Just advance the number of bytes that have
been processed and everything is fine.
This patch advances the variables even after the last operation even
though they aren't used any more afterwards to make things look more
uniform. A later patch will turn the whole thing into a loop and then
it actually starts making sense.
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
---
block/qcow2-cluster.c | 84 +++++++++++++++++----------------------------------
1 file changed, 28 insertions(+), 56 deletions(-)
diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c
index 4f43d41..78e7db9 100644
--- a/block/qcow2-cluster.c
+++ b/block/qcow2-cluster.c
@@ -1127,28 +1127,24 @@ int qcow2_alloc_cluster_offset(BlockDriverState *bs, uint64_t offset,
int n_start, int n_end, int *num, uint64_t *host_offset, QCowL2Meta **m)
{
BDRVQcowState *s = bs->opaque;
- int l2_index, ret, sectors;
- unsigned int nb_clusters, keep_clusters;
+ uint64_t start, remaining;
uint64_t cluster_offset;
uint64_t cur_bytes;
+ int ret;
trace_qcow2_alloc_clusters_offset(qemu_coroutine_self(), offset,
n_start, n_end);
+ assert(n_start * BDRV_SECTOR_SIZE == offset_into_cluster(s, offset));
+ offset = start_of_cluster(s, offset);
+
again:
+ start = offset + (n_start << BDRV_SECTOR_BITS);
+ remaining = (n_end - n_start) << BDRV_SECTOR_BITS;
cluster_offset = 0;
*host_offset = 0;
/*
- * Calculate the number of clusters to look for. We stop at L2 table
- * boundaries to keep things simple.
- */
- l2_index = offset_to_l2_index(s, offset);
- nb_clusters = MIN(size_to_clusters(s, n_end << BDRV_SECTOR_BITS),
- s->l2_size - l2_index);
- n_end = MIN(n_end, nb_clusters * s->cluster_sectors);
-
- /*
* Now start gathering as many contiguous clusters as possible:
*
* 1. Check for overlaps with in-flight allocations
@@ -1165,8 +1161,8 @@ again:
* cluster_offset to write to the same cluster and set up the right
* synchronisation between the in-flight request and the new one.
*/
- cur_bytes = (n_end - n_start) * BDRV_SECTOR_SIZE;
- ret = handle_dependencies(bs, offset, &cur_bytes);
+ cur_bytes = remaining;
+ ret = handle_dependencies(bs, start, &cur_bytes);
if (ret == -EAGAIN) {
goto again;
} else if (ret < 0) {
@@ -1177,33 +1173,28 @@ again:
* correctly during the next loop iteration. */
}
- nb_clusters = size_to_clusters(s, offset + cur_bytes)
- - (offset >> s->cluster_bits);
-
/*
* 2. Count contiguous COPIED clusters.
*/
- uint64_t tmp_bytes = cur_bytes;
- ret = handle_copied(bs, offset, &cluster_offset, &tmp_bytes, m);
+ ret = handle_copied(bs, start, &cluster_offset, &cur_bytes, m);
if (ret < 0) {
return ret;
} else if (ret) {
- keep_clusters =
- size_to_clusters(s, tmp_bytes + offset_into_cluster(s, offset));
- nb_clusters -= keep_clusters;
-
if (!*host_offset) {
*host_offset = start_of_cluster(s, cluster_offset);
}
+
+ start += cur_bytes;
+ remaining -= cur_bytes;
+ cluster_offset += cur_bytes;
+
+ cur_bytes = remaining;
} else if (cur_bytes == 0) {
- keep_clusters = 0;
goto done;
- } else {
- keep_clusters = 0;
}
/* If there is something left to allocate, do that now */
- if (nb_clusters == 0) {
+ if (remaining == 0) {
goto done;
}
@@ -1211,43 +1202,24 @@ again:
* 3. If the request still hasn't completed, allocate new clusters,
* considering any cluster_offset of steps 1c or 2.
*/
- int alloc_n_start;
- int alloc_n_end;
-
- if (keep_clusters != 0) {
- offset = start_of_cluster(s, offset
- + keep_clusters * s->cluster_size);
- cluster_offset = start_of_cluster(s, cluster_offset
- + keep_clusters * s->cluster_size);
-
- alloc_n_start = 0;
- alloc_n_end = n_end - keep_clusters * s->cluster_sectors;
- } else {
- alloc_n_start = n_start;
- alloc_n_end = n_end;
- }
-
- cur_bytes = MIN(cur_bytes, ((alloc_n_end - alloc_n_start) << BDRV_SECTOR_BITS));
-
- ret = handle_alloc(bs, offset, &cluster_offset, &cur_bytes, m);
+ ret = handle_alloc(bs, start, &cluster_offset, &cur_bytes, m);
if (ret < 0) {
return ret;
- }
+ } else if (ret) {
+ if (!*host_offset) {
+ *host_offset = start_of_cluster(s, cluster_offset);
+ }
- if (!*host_offset) {
- *host_offset = start_of_cluster(s, cluster_offset);
+ start += cur_bytes;
+ remaining -= cur_bytes;
+ cluster_offset += cur_bytes;
}
- nb_clusters = size_to_clusters(s, cur_bytes + offset_into_cluster(s, offset));
/* Some cleanup work */
done:
- sectors = (keep_clusters + nb_clusters) << (s->cluster_bits - 9);
- if (sectors > n_end) {
- sectors = n_end;
- }
-
- assert(sectors > n_start);
- *num = sectors - n_start;
+ *num = (n_end - n_start) - (remaining >> BDRV_SECTOR_BITS);
+ assert(*num > 0);
+ assert(*host_offset != 0);
return 0;
}
--
1.8.1.4
next prev parent reply other threads:[~2013-03-28 16:41 UTC|newest]
Thread overview: 24+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-03-28 16:40 [Qemu-devel] [PULL 00/23] Block patches Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 01/23] vl.c: call bdrv_init_with_whitelist() before cmdline parsing Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 02/23] qemu-iotests: More concurrent allocation scenarios Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 03/23] qcow2: Fix "total clusters" number in bdrv_check Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 04/23] qcow2: Remove bogus unlock of s->lock Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 05/23] qcow2: Handle dependencies earlier Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 06/23] qcow2: Improve check for overlapping allocations Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 07/23] qcow2: Change handle_dependency to byte granularity Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 08/23] qcow2: Decouple cluster allocation from cluster reuse code Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 09/23] qcow2: Factor out handle_alloc() Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 10/23] qcow2: handle_alloc(): Get rid of nb_clusters parameter Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 11/23] qcow2: handle_alloc(): Get rid of keep_clusters parameter Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 12/23] qcow2: Finalise interface of handle_alloc() Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 13/23] qcow2: Clean up handle_alloc() Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 14/23] qcow2: Factor out handle_copied() Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 15/23] qcow2: handle_copied(): Get rid of nb_clusters parameter Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 16/23] qcow2: handle_copied(): Get rid of keep_clusters parameter Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 17/23] qcow2: handle_copied(): Implement non-zero host_offset Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 18/23] qcow2: Prepare handle_alloc/copied() for byte granularity Stefan Hajnoczi
2013-03-28 16:40 ` Stefan Hajnoczi [this message]
2013-03-28 16:40 ` [Qemu-devel] [PATCH 20/23] qcow2: Allow requests with multiple l2metas Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 21/23] qcow2: Move cluster gathering to a non-looping loop Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 22/23] qcow2: Gather clusters in a looping loop Stefan Hajnoczi
2013-03-28 16:40 ` [Qemu-devel] [PATCH 23/23] block: Fix direct use of protocols as driver for bdrv_open() Stefan Hajnoczi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1364488837-15916-20-git-send-email-stefanha@redhat.com \
--to=stefanha@redhat.com \
--cc=aliguori@us.ibm.com \
--cc=kwolf@redhat.com \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).