[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [Qemu-devel] [PATCH 20/22] qcow2-dirty-bitmap: refcounts
From: |
Max Reitz |
Subject: |
Re: [Qemu-devel] [PATCH 20/22] qcow2-dirty-bitmap: refcounts |
Date: |
Mon, 10 Oct 2016 19:59:33 +0200 |
User-agent: |
Mozilla/5.0 (X11; Linux x86_64; rv:45.0) Gecko/20100101 Thunderbird/45.4.0 |
On 30.09.2016 12:53, Vladimir Sementsov-Ogievskiy wrote:
> Calculate refcounts for dirty bitmaps.
The commit message should mention that this is for qcow2's qemu-img
check implementation.
>
> Signed-off-by: Vladimir Sementsov-Ogievskiy <address@hidden>
> ---
> block/qcow2-bitmap.c | 60
> ++++++++++++++++++++++++++++++++++++++++++++++++++
> block/qcow2-refcount.c | 14 +++++++-----
> block/qcow2.h | 5 +++++
> 3 files changed, 74 insertions(+), 5 deletions(-)
>
> diff --git a/block/qcow2-bitmap.c b/block/qcow2-bitmap.c
> index 76f7e2b..6d9394a 100644
> --- a/block/qcow2-bitmap.c
> +++ b/block/qcow2-bitmap.c
> @@ -901,3 +901,63 @@ out:
> g_free(new_dir);
> g_free(dir);
> }
> +
> +int qcow2_dirty_bitmaps_refcounts(BlockDriverState *bs,
> + BdrvCheckResult *res,
> + void **refcount_table,
> + int64_t *refcount_table_size)
I'd rename this function to make clear that this is for checking the
refcounts, e.g. to "qcow2_check_dirty_bitmaps_refcounts" or
"qcow2_count_dirty_bitmaps_refcounts" or just
"qcow2_check_dirty_bitmaps". Probably the last one is the best because
this function should ideally perform a full check of the dirty bitmaps
extension.
> +{
> + BDRVQcow2State *s = bs->opaque;
> + uint8_t *dir;
> + Qcow2BitmapDirEntry *e;
> + Error *local_err = NULL;
> +
> + int i;
> + int ret = inc_refcounts(bs, res, refcount_table, refcount_table_size,
> + s->bitmap_directory_offset,
> + s->bitmap_directory_size);
> + if (ret < 0) {
> + return ret;
> + }
> +
> + dir = directory_read(bs, s->bitmap_directory_offset,
> + s->bitmap_directory_size, &local_err);
> + if (dir == NULL) {
> + error_report_err(local_err);
I think you should increment res->corruptions here.
> + return -EINVAL;
> + }
> +
> + for_each_bitmap_dir_entry(e, dir, s->bitmap_directory_size) {
> + uint64_t *bitmap_table = NULL;
I think you should call check_constraints() here.
> +
> + ret = inc_refcounts(bs, res, refcount_table, refcount_table_size,
> + e->bitmap_table_offset,
> + e->bitmap_table_size);
Probably rather e->bitmap_table_size * sizeof(uint64_t).
> + if (ret < 0) {
> + return ret;
> + }
> +
> + ret = bitmap_table_load(bs, e, &bitmap_table);
> + if (ret < 0) {
Again, it would make sense to increment res->corruptions here.
> + return ret;
> + }
> +
> + for (i = 0; i < e->bitmap_table_size; ++i) {
> + uint64_t off = be64_to_cpu(bitmap_table[i]);
> + if (off <= 1) {
> + continue;
> + }
As I said in some other patch, I'd write this condition differently
(with an offset mask, etc.).
Also, you should check that the offset is aligned to a cluster boundary
and that no unknown flags are set.
> +
> + ret = inc_refcounts(bs, res, refcount_table, refcount_table_size,
> + off, s->cluster_size);
> + if (ret < 0) {
> + g_free(bitmap_table);
> + return ret;
> + }
> + }
> +
> + g_free(bitmap_table);
> + }
> +
> + return 0;
dir is leaked here.
> +}
> diff --git a/block/qcow2-refcount.c b/block/qcow2-refcount.c
> index cbfb3fe..05bcc57 100644
> --- a/block/qcow2-refcount.c
> +++ b/block/qcow2-refcount.c
> @@ -1309,11 +1309,9 @@ static int realloc_refcount_array(BDRVQcow2State *s,
> void **array,
> *
> * Modifies the number of errors in res.
> */
> -static int inc_refcounts(BlockDriverState *bs,
> - BdrvCheckResult *res,
> - void **refcount_table,
> - int64_t *refcount_table_size,
> - int64_t offset, int64_t size)
> +int inc_refcounts(BlockDriverState *bs, BdrvCheckResult *res,
> + void **refcount_table, int64_t *refcount_table_size,
> + int64_t offset, int64_t size)
First, if you make this function public, you have to give it a qcow2_
prefix.
Second, if this function is public, it should have a name that makes
sense. inc_refcounts() sounds as if it's the same as update_refcount()
with an addend of 1. I'd rename it qcow2_inc_refcounts_imrt(), because
that's probably the shortest name I can come up with (and
qcow2-refcount.c explains what an IMRT is in some comment).
> {
> BDRVQcow2State *s = bs->opaque;
> uint64_t start, last, cluster_offset, k, refcount;
> @@ -1843,6 +1841,12 @@ static int calculate_refcounts(BlockDriverState *bs,
> BdrvCheckResult *res,
> return ret;
> }
>
> + /* dirty bitmaps */
> + ret = qcow2_dirty_bitmaps_refcounts(bs, res, refcount_table,
> nb_clusters);
> + if (ret < 0) {
> + return ret;
> + }
> +
> return check_refblocks(bs, res, fix, rebuild, refcount_table,
> nb_clusters);
> }
>
> diff --git a/block/qcow2.h b/block/qcow2.h
> index a5e7592..0a050ea 100644
> --- a/block/qcow2.h
> +++ b/block/qcow2.h
> @@ -563,6 +563,9 @@ int qcow2_check_metadata_overlap(BlockDriverState *bs,
> int ign, int64_t offset,
> int64_t size);
> int qcow2_pre_write_overlap_check(BlockDriverState *bs, int ign, int64_t
> offset,
> int64_t size);
> +int inc_refcounts(BlockDriverState *bs, BdrvCheckResult *res,
> + void **refcount_table, int64_t *refcount_table_size,
> + int64_t offset, int64_t size);
>
> int qcow2_change_refcount_order(BlockDriverState *bs, int refcount_order,
> BlockDriverAmendStatusCB *status_cb,
> @@ -616,6 +619,8 @@ int qcow2_read_snapshots(BlockDriverState *bs);
> int qcow2_read_bitmaps(BlockDriverState *bs, Error **errp);
>
> int qcow2_delete_bitmaps(BlockDriverState *bs);
> +int qcow2_dirty_bitmaps_refcounts(BlockDriverState *bs, BdrvCheckResult *res,
> + void **refcount_table, int64_t *refcount_table_size);
Normally we try to align parameters along the opening parenthesis as
long as there is enough space, and there is enough space here.
Max
>
> /* qcow2-cache.c functions */
> Qcow2Cache *qcow2_cache_create(BlockDriverState *bs, int num_tables);
>
signature.asc
Description: OpenPGP digital signature
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- Re: [Qemu-devel] [PATCH 20/22] qcow2-dirty-bitmap: refcounts,
Max Reitz <=