summaryrefslogtreecommitdiff
path: root/block/qcow2-bitmap.c
diff options
context:
space:
mode:
authorVladimir Sementsov-Ogievskiy <vsementsov@virtuozzo.com>2017-06-28 15:05:22 +0300
committerMax Reitz <mreitz@redhat.com>2017-07-11 17:44:59 +0200
commitda0eb242ad06b9e33300da7733a582bd61436fd2 (patch)
tree8280ce30db0d82906027d29d088bed76d029219d /block/qcow2-bitmap.c
parent67b792f5edec49fdd4e605d7a1d3a49095cd44bc (diff)
downloadqemu-da0eb242ad06b9e33300da7733a582bd61436fd2.tar.gz
qcow2: add .bdrv_can_store_new_dirty_bitmap
Realize .bdrv_can_store_new_dirty_bitmap interface. Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@virtuozzo.com> Reviewed-by: John Snow <jsnow@redhat.com> Reviewed-by: Max Reitz <mreitz@redhat.com> Message-id: 20170628120530.31251-23-vsementsov@virtuozzo.com Signed-off-by: Max Reitz <mreitz@redhat.com>
Diffstat (limited to 'block/qcow2-bitmap.c')
-rw-r--r--block/qcow2-bitmap.c51
1 files changed, 51 insertions, 0 deletions
diff --git a/block/qcow2-bitmap.c b/block/qcow2-bitmap.c
index f82478c02a..a8c7e1d190 100644
--- a/block/qcow2-bitmap.c
+++ b/block/qcow2-bitmap.c
@@ -1388,3 +1388,54 @@ int qcow2_reopen_bitmaps_ro(BlockDriverState *bs, Error **errp)
return 0;
}
+
+bool qcow2_can_store_new_dirty_bitmap(BlockDriverState *bs,
+ const char *name,
+ uint32_t granularity,
+ Error **errp)
+{
+ BDRVQcow2State *s = bs->opaque;
+ bool found;
+ Qcow2BitmapList *bm_list;
+
+ if (check_constraints_on_bitmap(bs, name, granularity, errp) != 0) {
+ goto fail;
+ }
+
+ if (s->nb_bitmaps == 0) {
+ return true;
+ }
+
+ if (s->nb_bitmaps >= QCOW2_MAX_BITMAPS) {
+ error_setg(errp,
+ "Maximum number of persistent bitmaps is already reached");
+ goto fail;
+ }
+
+ if (s->bitmap_directory_size + calc_dir_entry_size(strlen(name), 0) >
+ QCOW2_MAX_BITMAP_DIRECTORY_SIZE)
+ {
+ error_setg(errp, "Not enough space in the bitmap directory");
+ goto fail;
+ }
+
+ bm_list = bitmap_list_load(bs, s->bitmap_directory_offset,
+ s->bitmap_directory_size, errp);
+ if (bm_list == NULL) {
+ goto fail;
+ }
+
+ found = find_bitmap_by_name(bm_list, name);
+ bitmap_list_free(bm_list);
+ if (found) {
+ error_setg(errp, "Bitmap with the same name is already stored");
+ goto fail;
+ }
+
+ return true;
+
+fail:
+ error_prepend(errp, "Can't make bitmap '%s' persistent in '%s': ",
+ name, bdrv_get_device_or_node_name(bs));
+ return false;
+}