block: Freeze the backing chain for the duration of the commit job
Signed-off-by: Alberto Garcia <berto@igalia.com> Signed-off-by: Kevin Wolf <kwolf@redhat.com>
This commit is contained in:
parent
2cad1ebe70
commit
df827336ab
@ -39,6 +39,7 @@ typedef struct CommitBlockJob {
|
|||||||
BlockDriverState *base_bs;
|
BlockDriverState *base_bs;
|
||||||
BlockdevOnError on_error;
|
BlockdevOnError on_error;
|
||||||
bool base_read_only;
|
bool base_read_only;
|
||||||
|
bool chain_frozen;
|
||||||
char *backing_file_str;
|
char *backing_file_str;
|
||||||
} CommitBlockJob;
|
} CommitBlockJob;
|
||||||
|
|
||||||
@ -68,6 +69,9 @@ static int commit_prepare(Job *job)
|
|||||||
{
|
{
|
||||||
CommitBlockJob *s = container_of(job, CommitBlockJob, common.job);
|
CommitBlockJob *s = container_of(job, CommitBlockJob, common.job);
|
||||||
|
|
||||||
|
bdrv_unfreeze_backing_chain(s->commit_top_bs, s->base_bs);
|
||||||
|
s->chain_frozen = false;
|
||||||
|
|
||||||
/* Remove base node parent that still uses BLK_PERM_WRITE/RESIZE before
|
/* Remove base node parent that still uses BLK_PERM_WRITE/RESIZE before
|
||||||
* the normal backing chain can be restored. */
|
* the normal backing chain can be restored. */
|
||||||
blk_unref(s->base);
|
blk_unref(s->base);
|
||||||
@ -84,6 +88,10 @@ static void commit_abort(Job *job)
|
|||||||
CommitBlockJob *s = container_of(job, CommitBlockJob, common.job);
|
CommitBlockJob *s = container_of(job, CommitBlockJob, common.job);
|
||||||
BlockDriverState *top_bs = blk_bs(s->top);
|
BlockDriverState *top_bs = blk_bs(s->top);
|
||||||
|
|
||||||
|
if (s->chain_frozen) {
|
||||||
|
bdrv_unfreeze_backing_chain(s->commit_top_bs, s->base_bs);
|
||||||
|
}
|
||||||
|
|
||||||
/* Make sure commit_top_bs and top stay around until bdrv_replace_node() */
|
/* Make sure commit_top_bs and top stay around until bdrv_replace_node() */
|
||||||
bdrv_ref(top_bs);
|
bdrv_ref(top_bs);
|
||||||
bdrv_ref(s->commit_top_bs);
|
bdrv_ref(s->commit_top_bs);
|
||||||
@ -330,6 +338,11 @@ void commit_start(const char *job_id, BlockDriverState *bs,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (bdrv_freeze_backing_chain(commit_top_bs, base, errp) < 0) {
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
s->chain_frozen = true;
|
||||||
|
|
||||||
ret = block_job_add_bdrv(&s->common, "base", base, 0, BLK_PERM_ALL, errp);
|
ret = block_job_add_bdrv(&s->common, "base", base, 0, BLK_PERM_ALL, errp);
|
||||||
if (ret < 0) {
|
if (ret < 0) {
|
||||||
goto fail;
|
goto fail;
|
||||||
@ -362,6 +375,9 @@ void commit_start(const char *job_id, BlockDriverState *bs,
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
fail:
|
fail:
|
||||||
|
if (s->chain_frozen) {
|
||||||
|
bdrv_unfreeze_backing_chain(commit_top_bs, base);
|
||||||
|
}
|
||||||
if (s->base) {
|
if (s->base) {
|
||||||
blk_unref(s->base);
|
blk_unref(s->base);
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user