static int qcow_create(const char *filename, QemuOpts *opts, Error **errp)

{

    int header_size, backing_filename_len, l1_size, shift, i;

    QCowHeader header;

    uint8_t *tmp;

    int64_t total_size = 0;

    char *backing_file = NULL;

    Error *local_err = NULL;

    int ret;

    BlockBackend *qcow_blk;

    const char *encryptfmt = NULL;

    QDict *options;

    QDict *encryptopts = NULL;

    QCryptoBlockCreateOptions *crypto_opts = NULL;

    QCryptoBlock *crypto = NULL;



    /* Read out options */

    total_size = ROUND_UP(qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0),

                          BDRV_SECTOR_SIZE);

    if (total_size == 0) {

        error_setg(errp, "Image size is too small, cannot be zero length");

        ret = -EINVAL;

        goto cleanup;

    }



    backing_file = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FILE);

    encryptfmt = qemu_opt_get_del(opts, BLOCK_OPT_ENCRYPT_FORMAT);

    if (encryptfmt) {

        if (qemu_opt_get(opts, BLOCK_OPT_ENCRYPT)) {

            error_setg(errp, "Options " BLOCK_OPT_ENCRYPT " and "

                       BLOCK_OPT_ENCRYPT_FORMAT " are mutually exclusive");

            ret = -EINVAL;

            goto cleanup;

        }

    } else if (qemu_opt_get_bool_del(opts, BLOCK_OPT_ENCRYPT, false)) {

        encryptfmt = "aes";

    }



    ret = bdrv_create_file(filename, opts, &local_err);

    if (ret < 0) {

        error_propagate(errp, local_err);

        goto cleanup;

    }



    qcow_blk = blk_new_open(filename, NULL, NULL,

                            BDRV_O_RDWR | BDRV_O_RESIZE | BDRV_O_PROTOCOL,

                            &local_err);

    if (qcow_blk == NULL) {

        error_propagate(errp, local_err);

        ret = -EIO;

        goto cleanup;

    }



    blk_set_allow_write_beyond_eof(qcow_blk, true);



    ret = blk_truncate(qcow_blk, 0, PREALLOC_MODE_OFF, errp);

    if (ret < 0) {

        goto exit;

    }



    memset(&header, 0, sizeof(header));

    header.magic = cpu_to_be32(QCOW_MAGIC);

    header.version = cpu_to_be32(QCOW_VERSION);

    header.size = cpu_to_be64(total_size);

    header_size = sizeof(header);

    backing_filename_len = 0;

    if (backing_file) {

        if (strcmp(backing_file, "fat:")) {

            header.backing_file_offset = cpu_to_be64(header_size);

            backing_filename_len = strlen(backing_file);

            header.backing_file_size = cpu_to_be32(backing_filename_len);

            header_size += backing_filename_len;

        } else {

            /* special backing file for vvfat */

            g_free(backing_file);

            backing_file = NULL;

        }

        header.cluster_bits = 9; /* 512 byte cluster to avoid copying

                                    unmodified sectors */

        header.l2_bits = 12; /* 32 KB L2 tables */

    } else {

        header.cluster_bits = 12; /* 4 KB clusters */

        header.l2_bits = 9; /* 4 KB L2 tables */

    }

    header_size = (header_size + 7) & ~7;

    shift = header.cluster_bits + header.l2_bits;

    l1_size = (total_size + (1LL << shift) - 1) >> shift;



    header.l1_table_offset = cpu_to_be64(header_size);



    options = qemu_opts_to_qdict(opts, NULL);

    qdict_extract_subqdict(options, &encryptopts, "encrypt.");

    QDECREF(options);

    if (encryptfmt) {

        if (!g_str_equal(encryptfmt, "aes")) {

            error_setg(errp, "Unknown encryption format '%s', expected 'aes'",

                       encryptfmt);

            ret = -EINVAL;

            goto exit;

        }

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_AES);



        crypto_opts = block_crypto_create_opts_init(

            Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, errp);

        if (!crypto_opts) {

            ret = -EINVAL;

            goto exit;

        }



        crypto = qcrypto_block_create(crypto_opts, "encrypt.",

                                      NULL, NULL, NULL, errp);

        if (!crypto) {

            ret = -EINVAL;

            goto exit;

        }

    } else {

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_NONE);

    }



    /* write all the data */

    ret = blk_pwrite(qcow_blk, 0, &header, sizeof(header), 0);

    if (ret != sizeof(header)) {

        goto exit;

    }



    if (backing_file) {

        ret = blk_pwrite(qcow_blk, sizeof(header),

                         backing_file, backing_filename_len, 0);

        if (ret != backing_filename_len) {

            goto exit;

        }

    }



    tmp = g_malloc0(BDRV_SECTOR_SIZE);

    for (i = 0; i < DIV_ROUND_UP(sizeof(uint64_t) * l1_size, BDRV_SECTOR_SIZE);

         i++) {

        ret = blk_pwrite(qcow_blk, header_size + BDRV_SECTOR_SIZE * i,

                         tmp, BDRV_SECTOR_SIZE, 0);

        if (ret != BDRV_SECTOR_SIZE) {

            g_free(tmp);

            goto exit;

        }

    }



    g_free(tmp);

    ret = 0;

exit:

    blk_unref(qcow_blk);

cleanup:

    QDECREF(encryptopts);

    qcrypto_block_free(crypto);

    qapi_free_QCryptoBlockCreateOptions(crypto_opts);

    g_free(backing_file);

    return ret;

}

static int qcow_create(const char *filename, QemuOpts *opts, Error **errp)

{

    int header_size, backing_filename_len, l1_size, shift, i;

    QCowHeader header;

    uint8_t *tmp;

    int64_t total_size = 0;

    char *backing_file = NULL;

    Error *local_err = NULL;

    int ret;

    BlockBackend *qcow_blk;

    const char *encryptfmt = NULL;

    QDict *options;

    QDict *encryptopts = NULL;

    QCryptoBlockCreateOptions *crypto_opts = NULL;

    QCryptoBlock *crypto = NULL;



    

    total_size = ROUND_UP(qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0),

                          BDRV_SECTOR_SIZE);

    if (total_size == 0) {

        error_setg(errp, "Image size is too small, cannot be zero length");

        ret = -EINVAL;

        goto cleanup;

    }



    backing_file = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FILE);

    encryptfmt = qemu_opt_get_del(opts, BLOCK_OPT_ENCRYPT_FORMAT);

    if (encryptfmt) {

        if (qemu_opt_get(opts, BLOCK_OPT_ENCRYPT)) {

            error_setg(errp, "Options " BLOCK_OPT_ENCRYPT " and "

                       BLOCK_OPT_ENCRYPT_FORMAT " are mutually exclusive");

            ret = -EINVAL;

            goto cleanup;

        }

    } else if (qemu_opt_get_bool_del(opts, BLOCK_OPT_ENCRYPT, false)) {

        encryptfmt = "aes";

    }



    ret = bdrv_create_file(filename, opts, &local_err);

    if (ret < 0) {

        error_propagate(errp, local_err);

        goto cleanup;

    }



    qcow_blk = blk_new_open(filename, NULL, NULL,

                            BDRV_O_RDWR | BDRV_O_RESIZE | BDRV_O_PROTOCOL,

                            &local_err);

    if (qcow_blk == NULL) {

        error_propagate(errp, local_err);

        ret = -EIO;

        goto cleanup;

    }



    blk_set_allow_write_beyond_eof(qcow_blk, true);



    ret = blk_truncate(qcow_blk, 0, PREALLOC_MODE_OFF, errp);

    if (ret < 0) {

        goto exit;

    }



    memset(&header, 0, sizeof(header));

    header.magic = cpu_to_be32(QCOW_MAGIC);

    header.version = cpu_to_be32(QCOW_VERSION);

    header.size = cpu_to_be64(total_size);

    header_size = sizeof(header);

    backing_filename_len = 0;

    if (backing_file) {

        if (strcmp(backing_file, "fat:")) {

            header.backing_file_offset = cpu_to_be64(header_size);

            backing_filename_len = strlen(backing_file);

            header.backing_file_size = cpu_to_be32(backing_filename_len);

            header_size += backing_filename_len;

        } else {

            

            g_free(backing_file);

            backing_file = NULL;

        }

        header.cluster_bits = 9; 



        header.l2_bits = 12; 

    } else {

        header.cluster_bits = 12; 

        header.l2_bits = 9; 

    }

    header_size = (header_size + 7) & ~7;

    shift = header.cluster_bits + header.l2_bits;

    l1_size = (total_size + (1LL << shift) - 1) >> shift;



    header.l1_table_offset = cpu_to_be64(header_size);



    options = qemu_opts_to_qdict(opts, NULL);

    qdict_extract_subqdict(options, &encryptopts, "encrypt.");

    QDECREF(options);

    if (encryptfmt) {

        if (!g_str_equal(encryptfmt, "aes")) {

            error_setg(errp, "Unknown encryption format '%s', expected 'aes'",

                       encryptfmt);

            ret = -EINVAL;

            goto exit;

        }

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_AES);



        crypto_opts = block_crypto_create_opts_init(

            Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, errp);

        if (!crypto_opts) {

            ret = -EINVAL;

            goto exit;

        }



        crypto = qcrypto_block_create(crypto_opts, "encrypt.",

                                      NULL, NULL, NULL, errp);

        if (!crypto) {

            ret = -EINVAL;

            goto exit;

        }

    } else {

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_NONE);

    }



    

    ret = blk_pwrite(qcow_blk, 0, &header, sizeof(header), 0);

    if (ret != sizeof(header)) {

        goto exit;

    }



    if (backing_file) {

        ret = blk_pwrite(qcow_blk, sizeof(header),

                         backing_file, backing_filename_len, 0);

        if (ret != backing_filename_len) {

            goto exit;

        }

    }



    tmp = g_malloc0(BDRV_SECTOR_SIZE);

    for (i = 0; i < DIV_ROUND_UP(sizeof(uint64_t) * l1_size, BDRV_SECTOR_SIZE);

         i++) {

        ret = blk_pwrite(qcow_blk, header_size + BDRV_SECTOR_SIZE * i,

                         tmp, BDRV_SECTOR_SIZE, 0);

        if (ret != BDRV_SECTOR_SIZE) {

            g_free(tmp);

            goto exit;

        }

    }



    g_free(tmp);

    ret = 0;

exit:

    blk_unref(qcow_blk);

cleanup:

    QDECREF(encryptopts);

    qcrypto_block_free(crypto);

    qapi_free_QCryptoBlockCreateOptions(crypto_opts);

    g_free(backing_file);

    return ret;

}

    const char *encryptfmt = NULL;         encryptfmt = "aes";     const char *encryptfmt = NULL;         encryptfmt = "aes";
static int FUNC_0(const char *VAR_0, QemuOpts *VAR_1, Error **VAR_2)

{

    int VAR_3, VAR_4, VAR_5, VAR_6, VAR_7;

    QCowHeader header;

    uint8_t *tmp;

    int64_t total_size = 0;

    char *VAR_8 = NULL;

    Error *local_err = NULL;

    int VAR_9;

    BlockBackend *qcow_blk;

    const char *VAR_10 = NULL;

    QDict *options;

    QDict *encryptopts = NULL;

    QCryptoBlockCreateOptions *crypto_opts = NULL;

    QCryptoBlock *crypto = NULL;



    

    total_size = ROUND_UP(qemu_opt_get_size_del(VAR_1, BLOCK_OPT_SIZE, 0),

                          BDRV_SECTOR_SIZE);

    if (total_size == 0) {

        error_setg(VAR_2, "Image size is too small, cannot be zero length");

        VAR_9 = -EINVAL;

        goto cleanup;

    }



    VAR_8 = qemu_opt_get_del(VAR_1, BLOCK_OPT_BACKING_FILE);

    VAR_10 = qemu_opt_get_del(VAR_1, BLOCK_OPT_ENCRYPT_FORMAT);

    if (VAR_10) {

        if (qemu_opt_get(VAR_1, BLOCK_OPT_ENCRYPT)) {

            error_setg(VAR_2, "Options " BLOCK_OPT_ENCRYPT " and "

                       BLOCK_OPT_ENCRYPT_FORMAT " are mutually exclusive");

            VAR_9 = -EINVAL;

            goto cleanup;

        }

    } else if (qemu_opt_get_bool_del(VAR_1, BLOCK_OPT_ENCRYPT, false)) {

        VAR_10 = "aes";

    }



    VAR_9 = bdrv_create_file(VAR_0, VAR_1, &local_err);

    if (VAR_9 < 0) {

        error_propagate(VAR_2, local_err);

        goto cleanup;

    }



    qcow_blk = blk_new_open(VAR_0, NULL, NULL,

                            BDRV_O_RDWR | BDRV_O_RESIZE | BDRV_O_PROTOCOL,

                            &local_err);

    if (qcow_blk == NULL) {

        error_propagate(VAR_2, local_err);

        VAR_9 = -EIO;

        goto cleanup;

    }



    blk_set_allow_write_beyond_eof(qcow_blk, true);



    VAR_9 = blk_truncate(qcow_blk, 0, PREALLOC_MODE_OFF, VAR_2);

    if (VAR_9 < 0) {

        goto exit;

    }



    memset(&header, 0, sizeof(header));

    header.magic = cpu_to_be32(QCOW_MAGIC);

    header.version = cpu_to_be32(QCOW_VERSION);

    header.size = cpu_to_be64(total_size);

    VAR_3 = sizeof(header);

    VAR_4 = 0;

    if (VAR_8) {

        if (strcmp(VAR_8, "fat:")) {

            header.backing_file_offset = cpu_to_be64(VAR_3);

            VAR_4 = strlen(VAR_8);

            header.backing_file_size = cpu_to_be32(VAR_4);

            VAR_3 += VAR_4;

        } else {

            

            g_free(VAR_8);

            VAR_8 = NULL;

        }

        header.cluster_bits = 9; 



        header.l2_bits = 12; 

    } else {

        header.cluster_bits = 12; 

        header.l2_bits = 9; 

    }

    VAR_3 = (VAR_3 + 7) & ~7;

    VAR_6 = header.cluster_bits + header.l2_bits;

    VAR_5 = (total_size + (1LL << VAR_6) - 1) >> VAR_6;



    header.l1_table_offset = cpu_to_be64(VAR_3);



    options = qemu_opts_to_qdict(VAR_1, NULL);

    qdict_extract_subqdict(options, &encryptopts, "encrypt.");

    QDECREF(options);

    if (VAR_10) {

        if (!g_str_equal(VAR_10, "aes")) {

            error_setg(VAR_2, "Unknown encryption format '%s', expected 'aes'",

                       VAR_10);

            VAR_9 = -EINVAL;

            goto exit;

        }

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_AES);



        crypto_opts = block_crypto_create_opts_init(

            Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, VAR_2);

        if (!crypto_opts) {

            VAR_9 = -EINVAL;

            goto exit;

        }



        crypto = qcrypto_block_create(crypto_opts, "encrypt.",

                                      NULL, NULL, NULL, VAR_2);

        if (!crypto) {

            VAR_9 = -EINVAL;

            goto exit;

        }

    } else {

        header.crypt_method = cpu_to_be32(QCOW_CRYPT_NONE);

    }



    

    VAR_9 = blk_pwrite(qcow_blk, 0, &header, sizeof(header), 0);

    if (VAR_9 != sizeof(header)) {

        goto exit;

    }



    if (VAR_8) {

        VAR_9 = blk_pwrite(qcow_blk, sizeof(header),

                         VAR_8, VAR_4, 0);

        if (VAR_9 != VAR_4) {

            goto exit;

        }

    }



    tmp = g_malloc0(BDRV_SECTOR_SIZE);

    for (VAR_7 = 0; VAR_7 < DIV_ROUND_UP(sizeof(uint64_t) * VAR_5, BDRV_SECTOR_SIZE);

         VAR_7++) {

        VAR_9 = blk_pwrite(qcow_blk, VAR_3 + BDRV_SECTOR_SIZE * VAR_7,

                         tmp, BDRV_SECTOR_SIZE, 0);

        if (VAR_9 != BDRV_SECTOR_SIZE) {

            g_free(tmp);

            goto exit;

        }

    }



    g_free(tmp);

    VAR_9 = 0;

exit:

    blk_unref(qcow_blk);

cleanup:

    QDECREF(encryptopts);

    qcrypto_block_free(crypto);

    qapi_free_QCryptoBlockCreateOptions(crypto_opts);

    g_free(VAR_8);

    return VAR_9;

}

static int FUNC_0(const char *VAR_0, QemuOpts *VAR_1, Error **VAR_2)
{ int VAR_3, VAR_4, VAR_5, VAR_6, VAR_7; QCowHeader header; uint8_t *tmp; int64_t total_size = 0; char *VAR_8 = NULL; Error *local_err = NULL; int VAR_9; BlockBackend *qcow_blk; const char *VAR_10 = NULL; QDict *options; QDict *encryptopts = NULL; QCryptoBlockCreateOptions *crypto_opts = NULL; QCryptoBlock *crypto = NULL; total_size = ROUND_UP(qemu_opt_get_size_del(VAR_1, BLOCK_OPT_SIZE, 0),
BDRV_SECTOR_SIZE); if (total_size == 0) { error_setg(VAR_2, "Image size is too small, cannot be zero length"); VAR_9 = -EINVAL; goto cleanup; } VAR_8 = qemu_opt_get_del(VAR_1, BLOCK_OPT_BACKING_FILE); VAR_10 = qemu_opt_get_del(VAR_1, BLOCK_OPT_ENCRYPT_FORMAT); if (VAR_10) { if (qemu_opt_get(VAR_1, BLOCK_OPT_ENCRYPT)) { error_setg(VAR_2, "Options " BLOCK_OPT_ENCRYPT " and "
BLOCK_OPT_ENCRYPT_FORMAT " are mutually exclusive"); VAR_9 = -EINVAL; goto cleanup; } } else if (qemu_opt_get_bool_del(VAR_1, BLOCK_OPT_ENCRYPT, false)) { VAR_10 = "aes"; } VAR_9 = bdrv_create_file(VAR_0, VAR_1, &local_err); if (VAR_9 < 0) { error_propagate(VAR_2, local_err); goto cleanup; } qcow_blk = blk_new_open(VAR_0, NULL, NULL,
BDRV_O_RDWR | BDRV_O_RESIZE | BDRV_O_PROTOCOL,
&local_err); if (qcow_blk == NULL) { error_propagate(VAR_2, local_err); VAR_9 = -EIO; goto cleanup; } blk_set_allow_write_beyond_eof(qcow_blk, true); VAR_9 = blk_truncate(qcow_blk, 0, PREALLOC_MODE_OFF, VAR_2); if (VAR_9 < 0) { goto exit; } memset(&header, 0, sizeof(header)); header.magic = cpu_to_be32(QCOW_MAGIC); header.version = cpu_to_be32(QCOW_VERSION); header.size = cpu_to_be64(total_size); VAR_3 = sizeof(header); VAR_4 = 0; if (VAR_8) { if (strcmp(VAR_8, "fat:")) { header.backing_file_offset = cpu_to_be64(VAR_3); VAR_4 = strlen(VAR_8); header.backing_file_size = cpu_to_be32(VAR_4); VAR_3 += VAR_4; } else { g_free(VAR_8); VAR_8 = NULL; } header.cluster_bits = 9; header.l2_bits = 12; } else { header.cluster_bits = 12; header.l2_bits = 9; } VAR_3 = (VAR_3 + 7) & ~7; VAR_6 = header.cluster_bits + header.l2_bits; VAR_5 = (total_size + (1LL << VAR_6) - 1) >> VAR_6; header.l1_table_offset = cpu_to_be64(VAR_3); options = qemu_opts_to_qdict(VAR_1, NULL); qdict_extract_subqdict(options, &encryptopts, "encrypt."); QDECREF(options); if (VAR_10) { if (!g_str_equal(VAR_10, "aes")) { error_setg(VAR_2, "Unknown encryption format '%s', expected 'aes'",
VAR_10); VAR_9 = -EINVAL; goto exit; } header.crypt_method = cpu_to_be32(QCOW_CRYPT_AES); crypto_opts = block_crypto_create_opts_init(
Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, VAR_2); if (!crypto_opts) { VAR_9 = -EINVAL; goto exit; } crypto = qcrypto_block_create(crypto_opts, "encrypt.",
NULL, NULL, NULL, VAR_2); if (!crypto) { VAR_9 = -EINVAL; goto exit; } } else { header.crypt_method = cpu_to_be32(QCOW_CRYPT_NONE); } VAR_9 = blk_pwrite(qcow_blk, 0, &header, sizeof(header), 0); if (VAR_9 != sizeof(header)) { goto exit; } if (VAR_8) { VAR_9 = blk_pwrite(qcow_blk, sizeof(header),
VAR_8, VAR_4, 0); if (VAR_9 != VAR_4) { goto exit; } } tmp = g_malloc0(BDRV_SECTOR_SIZE); for (VAR_7 = 0; VAR_7 < DIV_ROUND_UP(sizeof(uint64_t) * VAR_5, BDRV_SECTOR_SIZE); VAR_7++) { VAR_9 = blk_pwrite(qcow_blk, VAR_3 + BDRV_SECTOR_SIZE * VAR_7,
tmp, BDRV_SECTOR_SIZE, 0); if (VAR_9 != BDRV_SECTOR_SIZE) { g_free(tmp); goto exit; } } g_free(tmp); VAR_9 = 0; exit:
blk_unref(qcow_blk); cleanup:
QDECREF(encryptopts); qcrypto_block_free(crypto); qapi_free_QCryptoBlockCreateOptions(crypto_opts); g_free(VAR_8); return VAR_9; }