From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([140.186.70.92]:45220) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Qe3rg-000772-7d for qemu-devel@nongnu.org; Tue, 05 Jul 2011 07:32:29 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1Qe3re-000244-FE for qemu-devel@nongnu.org; Tue, 05 Jul 2011 07:32:28 -0400 Received: from mail-iy0-f173.google.com ([209.85.210.173]:32835) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Qe3re-0001zz-45 for qemu-devel@nongnu.org; Tue, 05 Jul 2011 07:32:26 -0400 Received: by mail-iy0-f173.google.com with SMTP id 3so5889555iyb.4 for ; Tue, 05 Jul 2011 04:32:25 -0700 (PDT) From: Fam Zheng Date: Tue, 5 Jul 2011 19:31:14 +0800 Message-Id: <1309865478-32766-9-git-send-email-famcool@gmail.com> In-Reply-To: <1309865478-32766-1-git-send-email-famcool@gmail.com> References: <1309865478-32766-1-git-send-email-famcool@gmail.com> Subject: [Qemu-devel] [PATCH v8 08/12] VMDK: change get_cluster_offset return type List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: kwolf@redhat.com, Fam Zheng , hch@lst.de, stefanha@gmail.com The return type of get_cluster_offset was an offset that use 0 to denote 'not allocated', this will be no longer true for flat extents, as we see flat extent file as a single huge cluster whose offset is 0 and length is the whole file length. So now we use int return value, 0 means success and otherwise offset invalid. Signed-off-by: Fam Zheng --- block/vmdk.c | 79 ++++++++++++++++++++++++++++++--------------------------- 1 files changed, 42 insertions(+), 37 deletions(-) diff --git a/block/vmdk.c b/block/vmdk.c index 8dc58a8..f637d98 100644 --- a/block/vmdk.c +++ b/block/vmdk.c @@ -665,26 +665,31 @@ static int vmdk_L2update(VmdkExtent *extent, VmdkMetaData *m_data) return 0; } -static uint64_t get_cluster_offset(BlockDriverState *bs, +static int get_cluster_offset(BlockDriverState *bs, VmdkExtent *extent, VmdkMetaData *m_data, - uint64_t offset, int allocate) + uint64_t offset, + int allocate, + uint64_t *cluster_offset) { unsigned int l1_index, l2_offset, l2_index; int min_index, i, j; uint32_t min_count, *l2_table, tmp = 0; - uint64_t cluster_offset; if (m_data) m_data->valid = 0; + if (extent->flat) { + *cluster_offset = 0; + return 0; + } l1_index = (offset >> 9) / extent->l1_entry_sectors; if (l1_index >= extent->l1_size) { - return 0; + return -1; } l2_offset = extent->l1_table[l1_index]; if (!l2_offset) { - return 0; + return -1; } for (i = 0; i < L2_CACHE_SIZE; i++) { if (l2_offset == extent->l2_cache_offsets[i]) { @@ -714,28 +719,29 @@ static uint64_t get_cluster_offset(BlockDriverState *bs, l2_table, extent->l2_size * sizeof(uint32_t) ) != extent->l2_size * sizeof(uint32_t)) { - return 0; + return -1; } extent->l2_cache_offsets[min_index] = l2_offset; extent->l2_cache_counts[min_index] = 1; found: l2_index = ((offset >> 9) / extent->cluster_sectors) % extent->l2_size; - cluster_offset = le32_to_cpu(l2_table[l2_index]); + *cluster_offset = le32_to_cpu(l2_table[l2_index]); - if (!cluster_offset) { - if (!allocate) - return 0; + if (!*cluster_offset) { + if (!allocate) { + return -1; + } // Avoid the L2 tables update for the images that have snapshots. - cluster_offset = bdrv_getlength(extent->file); + *cluster_offset = bdrv_getlength(extent->file); bdrv_truncate( extent->file, - cluster_offset + (extent->cluster_sectors << 9) + *cluster_offset + (extent->cluster_sectors << 9) ); - cluster_offset >>= 9; - tmp = cpu_to_le32(cluster_offset); + *cluster_offset >>= 9; + tmp = cpu_to_le32(*cluster_offset); l2_table[l2_index] = tmp; /* First of all we write grain itself, to avoid race condition @@ -744,8 +750,8 @@ static uint64_t get_cluster_offset(BlockDriverState *bs, * or inappropriate VM shutdown. */ if (get_whole_cluster( - bs, extent, cluster_offset, offset, allocate) == -1) - return 0; + bs, extent, *cluster_offset, offset, allocate) == -1) + return -1; if (m_data) { m_data->offset = tmp; @@ -755,8 +761,8 @@ static uint64_t get_cluster_offset(BlockDriverState *bs, m_data->valid = 1; } } - cluster_offset <<= 9; - return cluster_offset; + *cluster_offset <<= 9; + return 0; } static VmdkExtent *find_extent(BDRVVmdkState *s, @@ -780,7 +786,6 @@ static int vmdk_is_allocated(BlockDriverState *bs, int64_t sector_num, int nb_sectors, int *pnum) { BDRVVmdkState *s = bs->opaque; - int64_t index_in_cluster, n, ret; uint64_t offset; VmdkExtent *extent; @@ -789,15 +794,13 @@ static int vmdk_is_allocated(BlockDriverState *bs, int64_t sector_num, if (!extent) { return 0; } - if (extent->flat) { - n = extent->end_sector - sector_num; - ret = 1; - } else { - offset = get_cluster_offset(bs, extent, NULL, sector_num * 512, 0); - index_in_cluster = sector_num % extent->cluster_sectors; - n = extent->cluster_sectors - index_in_cluster; - ret = offset ? 1 : 0; - } + ret = get_cluster_offset(bs, extent, NULL, + sector_num * 512, 0, &offset); + /* get_cluster_offset returning 0 means success */ + ret = !ret; + + index_in_cluster = sector_num % extent->cluster_sectors; + n = extent->cluster_sectors - index_in_cluster; if (n > nb_sectors) n = nb_sectors; *pnum = n; @@ -818,14 +821,15 @@ static int vmdk_read(BlockDriverState *bs, int64_t sector_num, if (!extent) { return -EIO; } - cluster_offset = get_cluster_offset( - bs, extent, NULL, sector_num << 9, 0); + ret = get_cluster_offset( + bs, extent, NULL, + sector_num << 9, 0, &cluster_offset); index_in_cluster = sector_num % extent->cluster_sectors; n = extent->cluster_sectors - index_in_cluster; if (n > nb_sectors) n = nb_sectors; - if (!cluster_offset) { - // try to read from parent image, if exist + if (ret) { + /* if not allocated, try to read from parent image, if exist */ if (bs->backing_hd) { if (!vmdk_is_cid_valid(bs)) return -1; @@ -851,7 +855,7 @@ static int vmdk_write(BlockDriverState *bs, int64_t sector_num, { BDRVVmdkState *s = bs->opaque; VmdkExtent *extent = NULL; - int n; + int n, ret; int64_t index_in_cluster; uint64_t cluster_offset; VmdkMetaData m_data; @@ -869,13 +873,14 @@ static int vmdk_write(BlockDriverState *bs, int64_t sector_num, if (!extent) { return -EIO; } - cluster_offset = get_cluster_offset( + ret = get_cluster_offset( bs, extent, &m_data, - sector_num << 9, 1); - if (!cluster_offset) { - return -1; + sector_num << 9, 1, + &cluster_offset); + if (ret) { + return -EINVAL; } index_in_cluster = sector_num % extent->cluster_sectors; n = extent->cluster_sectors - index_in_cluster;