[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH 62/97] block/backup: refactor: split out backup_calculate_cluster
From: |
Michael Roth |
Subject: |
[PATCH 62/97] block/backup: refactor: split out backup_calculate_cluster_size |
Date: |
Tue, 1 Oct 2019 18:45:41 -0500 |
From: Vladimir Sementsov-Ogievskiy <address@hidden>
Split out cluster_size calculation. Move copy-bitmap creation above
block-job creation, as we are going to share it with upcoming
backup-top filter, which also should be created before actual block job
creation.
Signed-off-by: Vladimir Sementsov-Ogievskiy <address@hidden>
Message-id: address@hidden
[mreitz: Dropped a paragraph from the commit message that was left over
from a previous version]
Signed-off-by: Max Reitz <address@hidden>
(cherry picked from commit ae6b12fa4cf7d54add35531c790aaf2bd6d833f3)
*prereq for 110571be4e
Signed-off-by: Michael Roth <address@hidden>
---
block/backup.c | 82 ++++++++++++++++++++++++++++++++------------------
1 file changed, 52 insertions(+), 30 deletions(-)
diff --git a/block/backup.c b/block/backup.c
index b54386b699..d1b94a6dbe 100644
--- a/block/backup.c
+++ b/block/backup.c
@@ -507,6 +507,42 @@ static const BlockJobDriver backup_job_driver = {
.drain = backup_drain,
};
+static int64_t backup_calculate_cluster_size(BlockDriverState *target,
+ Error **errp)
+{
+ int ret;
+ BlockDriverInfo bdi;
+
+ /*
+ * If there is no backing file on the target, we cannot rely on COW if our
+ * backup cluster size is smaller than the target cluster size. Even for
+ * targets with a backing file, try to avoid COW if possible.
+ */
+ ret = bdrv_get_info(target, &bdi);
+ if (ret == -ENOTSUP && !target->backing) {
+ /* Cluster size is not defined */
+ warn_report("The target block device doesn't provide "
+ "information about the block size and it doesn't have a "
+ "backing file. The default block size of %u bytes is "
+ "used. If the actual block size of the target exceeds "
+ "this default, the backup may be unusable",
+ BACKUP_CLUSTER_SIZE_DEFAULT);
+ return BACKUP_CLUSTER_SIZE_DEFAULT;
+ } else if (ret < 0 && !target->backing) {
+ error_setg_errno(errp, -ret,
+ "Couldn't determine the cluster size of the target image, "
+ "which has no backing file");
+ error_append_hint(errp,
+ "Aborting, since this may create an unusable destination image\n");
+ return ret;
+ } else if (ret < 0 && target->backing) {
+ /* Not fatal; just trudge on ahead. */
+ return BACKUP_CLUSTER_SIZE_DEFAULT;
+ }
+
+ return MAX(BACKUP_CLUSTER_SIZE_DEFAULT, bdi.cluster_size);
+}
+
BlockJob *backup_job_create(const char *job_id, BlockDriverState *bs,
BlockDriverState *target, int64_t speed,
MirrorSyncMode sync_mode, BdrvDirtyBitmap *sync_bitmap,
@@ -518,9 +554,10 @@ BlockJob *backup_job_create(const char *job_id,
BlockDriverState *bs,
JobTxn *txn, Error **errp)
{
int64_t len;
- BlockDriverInfo bdi;
BackupBlockJob *job = NULL;
int ret;
+ int64_t cluster_size;
+ HBitmap *copy_bitmap = NULL;
assert(bs);
assert(target);
@@ -582,6 +619,13 @@ BlockJob *backup_job_create(const char *job_id,
BlockDriverState *bs,
goto error;
}
+ cluster_size = backup_calculate_cluster_size(target, errp);
+ if (cluster_size < 0) {
+ goto error;
+ }
+
+ copy_bitmap = hbitmap_alloc(len, ctz32(cluster_size));
+
/* job->len is fixed, so we can't allow resize */
job = block_job_create(job_id, &backup_job_driver, txn, bs,
BLK_PERM_CONSISTENT_READ,
@@ -610,35 +654,9 @@ BlockJob *backup_job_create(const char *job_id,
BlockDriverState *bs,
/* Detect image-fleecing (and similar) schemes */
job->serialize_target_writes = bdrv_chain_contains(target, bs);
-
- /* If there is no backing file on the target, we cannot rely on COW if our
- * backup cluster size is smaller than the target cluster size. Even for
- * targets with a backing file, try to avoid COW if possible. */
- ret = bdrv_get_info(target, &bdi);
- if (ret == -ENOTSUP && !target->backing) {
- /* Cluster size is not defined */
- warn_report("The target block device doesn't provide "
- "information about the block size and it doesn't have a "
- "backing file. The default block size of %u bytes is "
- "used. If the actual block size of the target exceeds "
- "this default, the backup may be unusable",
- BACKUP_CLUSTER_SIZE_DEFAULT);
- job->cluster_size = BACKUP_CLUSTER_SIZE_DEFAULT;
- } else if (ret < 0 && !target->backing) {
- error_setg_errno(errp, -ret,
- "Couldn't determine the cluster size of the target image, "
- "which has no backing file");
- error_append_hint(errp,
- "Aborting, since this may create an unusable destination image\n");
- goto error;
- } else if (ret < 0 && target->backing) {
- /* Not fatal; just trudge on ahead. */
- job->cluster_size = BACKUP_CLUSTER_SIZE_DEFAULT;
- } else {
- job->cluster_size = MAX(BACKUP_CLUSTER_SIZE_DEFAULT, bdi.cluster_size);
- }
-
- job->copy_bitmap = hbitmap_alloc(len, ctz32(job->cluster_size));
+ job->cluster_size = cluster_size;
+ job->copy_bitmap = copy_bitmap;
+ copy_bitmap = NULL;
job->use_copy_range = true;
job->copy_range_size = MIN_NON_ZERO(blk_get_max_transfer(job->common.blk),
blk_get_max_transfer(job->target));
@@ -654,6 +672,10 @@ BlockJob *backup_job_create(const char *job_id,
BlockDriverState *bs,
return &job->common;
error:
+ if (copy_bitmap) {
+ assert(!job || !job->copy_bitmap);
+ hbitmap_free(copy_bitmap);
+ }
if (sync_bitmap) {
bdrv_reclaim_dirty_bitmap(bs, sync_bitmap, NULL);
}
--
2.17.1
- [PATCH 88/97] curl: Check completion in curl_multi_do(), (continued)
- [PATCH 88/97] curl: Check completion in curl_multi_do(), Michael Roth, 2019/10/01
- [PATCH 87/97] curl: Keep *socket until the end of curl_sock_cb(), Michael Roth, 2019/10/01
- [PATCH 17/97] block: Drain source node in bdrv_replace_node(), Michael Roth, 2019/10/01
- [PATCH 57/97] tpm_emulator: Translate TPM error codes to strings, Michael Roth, 2019/10/01
- [PATCH 81/97] iotests: Test blockdev-create for vpc, Michael Roth, 2019/10/01
- [PATCH 79/97] iotests: Restrict file Python tests to file, Michael Roth, 2019/10/01
- [PATCH 65/97] util/hbitmap: update orig_size on truncate, Michael Roth, 2019/10/01
- [PATCH 66/97] iotests: Test incremental backup after truncation, Michael Roth, 2019/10/01
- [PATCH 04/97] megasas: fix mapped frame size, Michael Roth, 2019/10/01
- [PATCH 70/97] Revert "ide/ahci: Check for -ECANCELED in aio callbacks", Michael Roth, 2019/10/01
- [PATCH 62/97] block/backup: refactor: split out backup_calculate_cluster_size,
Michael Roth <=
- [PATCH 67/97] mirror: Only mirror granularity-aligned chunks, Michael Roth, 2019/10/01
- [PATCH 59/97] block/backup: move to copy_bitmap with granularity, Michael Roth, 2019/10/01
- [PATCH 72/97] dma-helpers: ensure AIO callback is invoked after cancellation, Michael Roth, 2019/10/01
- [PATCH 77/97] vpc: Return 0 from vpc_co_create() on success, Michael Roth, 2019/10/01
- [PATCH 83/97] block/create: Do not abort if a block driver is not available, Michael Roth, 2019/10/01
- [PATCH 76/97] iotests: add testing shim for script-style python tests, Michael Roth, 2019/10/01
- [PATCH 71/97] qcow2: Fix the calculation of the maximum L2 cache size, Michael Roth, 2019/10/01
- [PATCH 86/97] curl: Keep pointer to the CURLState in CURLSocket, Michael Roth, 2019/10/01
- [PATCH 61/97] block/backup: unify different modes code path, Michael Roth, 2019/10/01
- [PATCH 89/97] curl: Pass CURLSocket to curl_multi_do(), Michael Roth, 2019/10/01