To create a Gluks header image, use the command as follows: $ qemu-img create --object secret,id=sec0,data=abc123 -f gluks > -o cipher-alg=aes-256,cipher-mode=xts -o key-secret=sec0 > cipher.gluks
Signed-off-by: Hyman Huang <yong.hu...@smartx.com> --- block.c | 5 +++++ block/generic-luks.c | 53 +++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 57 insertions(+), 1 deletion(-) diff --git a/block.c b/block.c index bfb0861ec6..cc9a517a25 100644 --- a/block.c +++ b/block.c @@ -7517,6 +7517,11 @@ void bdrv_img_create(const char *filename, const char *fmt, goto out; } + if (!strcmp(fmt, "gluks")) { + qemu_opt_set(opts, "size", "0M", &local_err); + size = 0; + } + if (size == -1) { error_setg(errp, "Image creation needs a size parameter"); goto out; diff --git a/block/generic-luks.c b/block/generic-luks.c index 32cbedc86f..579f01c4b0 100644 --- a/block/generic-luks.c +++ b/block/generic-luks.c @@ -145,7 +145,58 @@ static int coroutine_fn GRAPH_UNLOCKED gluks_co_create_opts(BlockDriver *drv, const char *filename, QemuOpts *opts, Error **errp) { - return 0; + QCryptoBlockCreateOptions *create_opts = NULL; + BlockDriverState *bs = NULL; + QDict *cryptoopts; + int ret; + + if (qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0) != 0) { + info_report("gluks format image need not size parameter, ignore it"); + } + + cryptoopts = qemu_opts_to_qdict_filtered(opts, NULL, + &gluks_create_opts_luks, + true); + + qdict_put_str(cryptoopts, "format", + QCryptoBlockFormat_str(Q_CRYPTO_BLOCK_FORMAT_GLUKS)); + + create_opts = block_crypto_create_opts_init(cryptoopts, errp); + if (!create_opts) { + ret = -EINVAL; + goto fail; + } + + /* Create protocol layer */ + ret = bdrv_co_create_file(filename, opts, errp); + if (ret < 0) { + goto fail; + } + + bs = bdrv_co_open(filename, NULL, NULL, + BDRV_O_RDWR | BDRV_O_RESIZE | BDRV_O_PROTOCOL, errp); + if (!bs) { + ret = -EINVAL; + goto fail; + } + /* Create format layer */ + ret = block_crypto_co_create_generic(bs, 0, create_opts, 0, errp); + if (ret < 0) { + goto fail; + } + + ret = 0; +fail: + /* + * If an error occurred, delete 'filename'. Even if the file existed + * beforehand, it has been truncated and corrupted in the process. + */ + if (ret) { + bdrv_graph_co_rdlock(); + bdrv_co_delete_file_noerr(bs); + bdrv_graph_co_rdunlock(); + } + return ret; } static void -- 2.39.1