[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 12/18] block/dirty-bitmap: Add bdrv_dirty_iter_next_
From: |
Max Reitz |
Subject: |
[Qemu-devel] [PATCH 12/18] block/dirty-bitmap: Add bdrv_dirty_iter_next_area |
Date: |
Wed, 13 Sep 2017 20:19:04 +0200 |
This new function allows to look for a consecutively dirty area in a
dirty bitmap.
Signed-off-by: Max Reitz <address@hidden>
---
include/block/dirty-bitmap.h | 2 ++
block/dirty-bitmap.c | 52 ++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 54 insertions(+)
diff --git a/include/block/dirty-bitmap.h b/include/block/dirty-bitmap.h
index a79a58d2c3..7654748700 100644
--- a/include/block/dirty-bitmap.h
+++ b/include/block/dirty-bitmap.h
@@ -90,6 +90,8 @@ void bdrv_set_dirty_bitmap_locked(BdrvDirtyBitmap *bitmap,
void bdrv_reset_dirty_bitmap_locked(BdrvDirtyBitmap *bitmap,
int64_t cur_sector, int64_t nr_sectors);
int64_t bdrv_dirty_iter_next(BdrvDirtyBitmapIter *iter);
+bool bdrv_dirty_iter_next_area(BdrvDirtyBitmapIter *iter, uint64_t max_offset,
+ uint64_t *offset, int *bytes);
void bdrv_set_dirty_iter(BdrvDirtyBitmapIter *hbi, int64_t sector_num);
int64_t bdrv_get_dirty_count(BdrvDirtyBitmap *bitmap);
int64_t bdrv_get_meta_dirty_count(BdrvDirtyBitmap *bitmap);
diff --git a/block/dirty-bitmap.c b/block/dirty-bitmap.c
index aee57cf8c8..81b2f78016 100644
--- a/block/dirty-bitmap.c
+++ b/block/dirty-bitmap.c
@@ -550,6 +550,58 @@ int64_t bdrv_dirty_iter_next(BdrvDirtyBitmapIter *iter)
return hbitmap_iter_next(&iter->hbi, true);
}
+/**
+ * Return the next consecutively dirty area in the dirty bitmap
+ * belonging to the given iterator @iter.
+ *
+ * @max_offset: Maximum value that may be returned for
+ * *offset + *bytes
+ * @offset: Will contain the start offset of the next dirty area
+ * @bytes: Will contain the length of the next dirty area
+ *
+ * Returns: True if a dirty area could be found before max_offset
+ * (which means that *offset and *bytes then contain valid
+ * values), false otherwise.
+ */
+bool bdrv_dirty_iter_next_area(BdrvDirtyBitmapIter *iter, uint64_t max_offset,
+ uint64_t *offset, int *bytes)
+{
+ uint32_t granularity = bdrv_dirty_bitmap_granularity(iter->bitmap);
+ uint64_t gran_max_offset;
+ int sector_gran = granularity >> BDRV_SECTOR_BITS;
+ int64_t ret;
+ int size;
+
+ if (DIV_ROUND_UP(max_offset, BDRV_SECTOR_SIZE) == iter->bitmap->size) {
+ /* If max_offset points to the image end, round it up by the
+ * bitmap granularity */
+ gran_max_offset = ROUND_UP(max_offset, granularity);
+ } else {
+ gran_max_offset = max_offset;
+ }
+
+ ret = hbitmap_iter_next(&iter->hbi, false);
+ if (ret < 0 || (ret << BDRV_SECTOR_BITS) + granularity > gran_max_offset) {
+ return false;
+ }
+
+ *offset = ret << BDRV_SECTOR_BITS;
+ size = 0;
+
+ assert(granularity <= INT_MAX);
+
+ do {
+ /* Advance iterator */
+ ret = hbitmap_iter_next(&iter->hbi, true);
+ size += granularity;
+ } while ((ret << BDRV_SECTOR_BITS) + granularity <= gran_max_offset &&
+ hbitmap_iter_next(&iter->hbi, false) == ret + sector_gran &&
+ size <= INT_MAX - granularity);
+
+ *bytes = MIN(size, max_offset - *offset);
+ return true;
+}
+
/* Called within bdrv_dirty_bitmap_lock..unlock */
void bdrv_set_dirty_bitmap_locked(BdrvDirtyBitmap *bitmap,
int64_t cur_sector, int64_t nr_sectors)
--
2.13.5
- Re: [Qemu-devel] [PATCH 05/18] block/mirror: Convert to coroutines, (continued)
- [Qemu-devel] [PATCH 06/18] block/mirror: Use CoQueue to wait on in-flight ops, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 07/18] block/mirror: Wait for in-flight op conflicts, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 08/18] block/mirror: Use source as a BdrvChild, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 09/18] block: Generalize should_update_child() rule, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 10/18] block/mirror: Make source the file child, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 11/18] hbitmap: Add @advance param to hbitmap_iter_next(), Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 12/18] block/dirty-bitmap: Add bdrv_dirty_iter_next_area,
Max Reitz <=
- [Qemu-devel] [PATCH 13/18] block/mirror: Keep write perm for pending writes, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 14/18] block/mirror: Distinguish active from passive ops, Max Reitz, 2017/09/13
- [Qemu-devel] [PATCH 15/18] block/mirror: Add active mirroring, Max Reitz, 2017/09/13