Commit 4254d01c authored by Kevin Wolf's avatar Kevin Wolf
Browse files

Merge remote-tracking branch 'mreitz/tags/pull-block-2017-10-26' into queue-block



Block patches

# gpg: Signature made Thu Oct 26 15:01:20 2017 CEST
# gpg:                using RSA key F407DB0061D5CF40
# gpg: Good signature from "Max Reitz <mreitz@redhat.com>"
# Primary key fingerprint: 91BE B60A 30DB 3E88 57D1  1829 F407 DB00 61D5 CF40

* mreitz/tags/pull-block-2017-10-26:
  iotests: Add cluster_size=64k to 125
  qcow2: Always execute preallocate() in a coroutine
  qcow2: Fix unaligned preallocated truncation
  qcow2: Emit errp when truncating the image tail
  iotests: Filter actual image size in 184 and 191
  iotests: Pull _filter_actual_image_size from 67/87
  iotests: Add test for dataplane mirroring
  qcow2: Use BDRV_SECTOR_BITS instead of its literal value

Signed-off-by: default avatarKevin Wolf <kwolf@redhat.com>
parents 67e56472 4c112a39
Loading
Loading
Loading
Loading
+44 −15
Original line number Diff line number Diff line
@@ -1139,7 +1139,7 @@ static int qcow2_do_open(BlockDriverState *bs, QDict *options, int flags,

    s->cluster_bits = header.cluster_bits;
    s->cluster_size = 1 << s->cluster_bits;
    s->cluster_sectors = 1 << (s->cluster_bits - 9);
    s->cluster_sectors = 1 << (s->cluster_bits - BDRV_SECTOR_BITS);

    /* Initialise version 3 header fields */
    if (header.version == 2) {
@@ -1636,7 +1636,7 @@ static int64_t coroutine_fn qcow2_co_get_block_status(BlockDriverState *bs,

    bytes = MIN(INT_MAX, nb_sectors * BDRV_SECTOR_SIZE);
    qemu_co_mutex_lock(&s->lock);
    ret = qcow2_get_cluster_offset(bs, sector_num << 9, &bytes,
    ret = qcow2_get_cluster_offset(bs, sector_num << BDRV_SECTOR_BITS, &bytes,
                                   &cluster_offset);
    qemu_co_mutex_unlock(&s->lock);
    if (ret < 0) {
@@ -2460,6 +2460,14 @@ static int qcow2_set_up_encryption(BlockDriverState *bs, const char *encryptfmt,
}


typedef struct PreallocCo {
    BlockDriverState *bs;
    uint64_t offset;
    uint64_t new_length;

    int ret;
} PreallocCo;

/**
 * Preallocates metadata structures for data clusters between @offset (in the
 * guest disk) and @new_length (which is thus generally the new guest disk
@@ -2467,9 +2475,12 @@ static int qcow2_set_up_encryption(BlockDriverState *bs, const char *encryptfmt,
 *
 * Returns: 0 on success, -errno on failure.
 */
static int preallocate(BlockDriverState *bs,
                       uint64_t offset, uint64_t new_length)
static void coroutine_fn preallocate_co(void *opaque)
{
    PreallocCo *params = opaque;
    BlockDriverState *bs = params->bs;
    uint64_t offset = params->offset;
    uint64_t new_length = params->new_length;
    BDRVQcow2State *s = bs->opaque;
    uint64_t bytes;
    uint64_t host_offset = 0;
@@ -2477,9 +2488,7 @@ static int preallocate(BlockDriverState *bs,
    int ret;
    QCowL2Meta *meta;

    if (qemu_in_coroutine()) {
    qemu_co_mutex_lock(&s->lock);
    }

    assert(offset <= new_length);
    bytes = new_length - offset;
@@ -2533,10 +2542,28 @@ static int preallocate(BlockDriverState *bs,
    ret = 0;

done:
    if (qemu_in_coroutine()) {
    qemu_co_mutex_unlock(&s->lock);
    params->ret = ret;
}
    return ret;

static int preallocate(BlockDriverState *bs,
                       uint64_t offset, uint64_t new_length)
{
    PreallocCo params = {
        .bs         = bs,
        .offset     = offset,
        .new_length = new_length,
        .ret        = -EINPROGRESS,
    };

    if (qemu_in_coroutine()) {
        preallocate_co(&params);
    } else {
        Coroutine *co = qemu_coroutine_create(preallocate_co, &params);
        bdrv_coroutine_enter(bs, co);
        BDRV_POLL_WHILE(bs, params.ret == -EINPROGRESS);
    }
    return params.ret;
}

/* qcow2_refcount_metadata_size:
@@ -3145,12 +3172,13 @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
            return last_cluster;
        }
        if ((last_cluster + 1) * s->cluster_size < old_file_size) {
            ret = bdrv_truncate(bs->file, (last_cluster + 1) * s->cluster_size,
                                PREALLOC_MODE_OFF, NULL);
            if (ret < 0) {
                warn_report("Failed to truncate the tail of the image: %s",
                            strerror(-ret));
                ret = 0;
            Error *local_err = NULL;

            bdrv_truncate(bs->file, (last_cluster + 1) * s->cluster_size,
                          PREALLOC_MODE_OFF, &local_err);
            if (local_err) {
                warn_reportf_err(local_err,
                                 "Failed to truncate the tail of the image: ");
            }
        }
    } else {
@@ -3187,6 +3215,7 @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
                             "Failed to inquire current file length");
            return old_file_size;
        }
        old_file_size = ROUND_UP(old_file_size, s->cluster_size);

        nb_new_data_clusters = DIV_ROUND_UP(offset - old_length,
                                            s->cluster_size);
+1 −1
Original line number Diff line number Diff line
@@ -56,7 +56,7 @@ _filter_qmp_events()
function run_qemu()
{
    do_run_qemu "$@" 2>&1 | _filter_testdir | _filter_qmp | _filter_qemu \
                          | sed -e 's/\("actual-size":\s*\)[0-9]\+/\1SIZE/g' \
                          | _filter_actual_image_size \
                          | _filter_generated_node_ids | _filter_qmp_events
}

+1 −1
Original line number Diff line number Diff line
@@ -46,7 +46,7 @@ function run_qemu()
{
    do_run_qemu "$@" 2>&1 | _filter_testdir | _filter_qmp \
                          | _filter_qemu | _filter_imgfmt \
                          | sed -e 's/\("actual-size":\s*\)[0-9]\+/\1SIZE/g'
                          | _filter_actual_image_size
}

size=128M
+5 −2
Original line number Diff line number Diff line
@@ -69,13 +69,15 @@ fi
# in B
CREATION_SIZE=$((2 * 1024 * 1024 - 48 * 1024))

# 512 is the actual test -- but it's good to test 64k as well, just to be sure.
for cluster_size in 512 64k; do
# in kB
for GROWTH_SIZE in 16 48 80; do
    for create_mode in off metadata falloc full; do
        for growth_mode in off metadata falloc full; do
            echo "--- growth_size=$GROWTH_SIZE create_mode=$create_mode growth_mode=$growth_mode ---"
            echo "--- cluster_size=$cluster_size growth_size=$GROWTH_SIZE create_mode=$create_mode growth_mode=$growth_mode ---"

            IMGOPTS="preallocation=$create_mode,cluster_size=512" _make_test_img ${CREATION_SIZE}
            IMGOPTS="preallocation=$create_mode,cluster_size=$cluster_size" _make_test_img ${CREATION_SIZE}
            $QEMU_IMG resize -f "$IMGFMT" --preallocation=$growth_mode "$TEST_IMG" +${GROWTH_SIZE}K

            host_size_0=$(get_image_size_on_host)
@@ -123,6 +125,7 @@ for GROWTH_SIZE in 16 48 80; do
        done
    done
done
done

# success, all done
echo '*** done'
+432 −48

File changed.

Preview size limit exceeded, changes collapsed.

Loading