https://bugzilla.redhat.com/show_bug.cgi?id=1526382 As of QEMU 2.9, qemu-img has enforced using the "encrypt.key-secret" in order to create a qcow[2] encrypted volume. Thus, the existing code to create an encrypted volume using qcow[2] encryption techniques will fail, such as : $ qemu-img create -f qcow2 -b /dev/null \ -o backing_fmt=raw,encryption=on \ demo.tmp 5242880K Formatting 'demo.tmp', fmt=qcow2 size=5368709120 backing_file=/dev/null backing_fmt=raw encryption=on cluster_size=65536 lazy_refcounts=off refcount_bits=16 qemu-img: demo.tmp: Parameter 'encrypt.key-secret' is required for cipher $ This patch will resolve this by adding the correct parameters for the creation. The new format of parameters roughly follows that of LUKS encryption model with a few minor differences: 1. Usage of "encrypt.key-secret=$alias" instead of just plain "key-secret=$alias" as the parameter. 2. Usage of "encrypt.format=aes" instead of "encryption=on" The result is the following command syntax for the same example: $ qemu-img create -f qcow2 -b /dev/null \ --object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ -o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0 \ demo.tmp 5242880K Formatting 'test.img', fmt=qcow2 size=5368709120 backing_file=/dev/null backing_fmt=raw encrypt.format=aes encrypt.key-secret=sec0 cluster_size=65536 lazy_refcounts=off refcount_bits=16 $ Thus this patch removes the LUKS specific checks in a few places and alters the algorithms as necessary in order to allow either form of encryption. The storagevolxml2argvtest.c test is adjusted to pass a dummy path to the secret file and the outputs adjusted to illustrate the new format for the various arguments. This patch requires usage of the secrets object and model. There is no plan for backwards compatibility for qcow[2] encryption. The desire is to move towards usage of LUKS encryption anyway. NB: Although the qemu-img convert examples change in the test output, they are essentially still broken (they wouldn't work before this patch either for the same reasons create fails). A follow-up patch will alter the algorithm and syntax. Signed-off-by: John Ferlan <jferlan@xxxxxxxxxx> --- src/storage/storage_util.c | 24 +++++++++++----------- src/util/virqemu.c | 10 +++++++-- src/util/virqemu.h | 3 ++- tests/storagevolxml2argvdata/qcow2-1.1.argv | 4 +++- tests/storagevolxml2argvdata/qcow2-compat.argv | 4 +++- .../qcow2-from-logical-compat.argv | 3 ++- tests/storagevolxml2argvdata/qcow2-lazy.argv | 6 ++++-- .../qcow2-nobacking-convert-prealloc-compat.argv | 4 +++- .../qcow2-nobacking-prealloc-compat.argv | 4 +++- .../qcow2-nocapacity-convert-prealloc.argv | 7 ++++--- tests/storagevolxml2argvdata/qcow2-nocapacity.argv | 4 +++- .../storagevolxml2argvdata/qcow2-nocow-compat.argv | 6 ++++-- tests/storagevolxml2argvdata/qcow2-nocow.argv | 3 ++- tests/storagevolxml2argvtest.c | 2 +- 14 files changed, 54 insertions(+), 30 deletions(-) diff --git a/src/storage/storage_util.c b/src/storage/storage_util.c index 554fc757ed..a8a6a3e401 100644 --- a/src/storage/storage_util.c +++ b/src/storage/storage_util.c @@ -827,11 +827,10 @@ storageBackendCreateQemuImgOpts(virStorageEncryptionInfoDefPtr enc, virBufferAsprintf(&buf, "backing_fmt=%s,", virStorageFileFormatTypeToString(info.backingFormat)); - if (info.format == VIR_STORAGE_FILE_RAW && enc) { - virQEMUBuildQemuImgKeySecretOpts(&buf, enc, info.secretAlias); - } else { - if (info.encryption) - virBufferAddLit(&buf, "encryption=on,"); + if (enc) { + bool qcow = (info.format == VIR_STORAGE_FILE_QCOW || + info.format == VIR_STORAGE_FILE_QCOW2); + virQEMUBuildQemuImgKeySecretOpts(&buf, enc, info.secretAlias, qcow); } if (info.preallocate) { @@ -1231,8 +1230,12 @@ virStorageBackendCreateQemuImgCmdFromVol(virStoragePoolObjPtr pool, if (info.backingPath) virCommandAddArgList(cmd, "-b", info.backingPath, NULL); - if (info.format == VIR_STORAGE_FILE_RAW && vol->target.encryption && - vol->target.encryption->format == VIR_STORAGE_ENCRYPTION_FORMAT_LUKS) { + if (vol->target.encryption) { + if (!secretPath) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("path to secret data file is required")); + return NULL; + } if (virAsprintf(&info.secretAlias, "%s_encrypt0", vol->name) < 0) goto error; if (storageBackendCreateQemuImgSecretObject(cmd, info.secretPath, @@ -1344,11 +1347,8 @@ storageBackendGenerateSecretData(virStoragePoolObjPtr pool, return -1; } - if (vol->target.format == VIR_STORAGE_FILE_RAW && - enc->format == VIR_STORAGE_ENCRYPTION_FORMAT_LUKS) { - if (!(*secretPath = storageBackendCreateQemuImgSecretPath(pool, vol))) - return -1; - } + if (!(*secretPath = storageBackendCreateQemuImgSecretPath(pool, vol))) + return -1; return 0; } diff --git a/src/util/virqemu.c b/src/util/virqemu.c index 04cd71605e..b20d09d945 100644 --- a/src/util/virqemu.c +++ b/src/util/virqemu.c @@ -307,6 +307,7 @@ virQEMUBuildBufferEscapeComma(virBufferPtr buf, const char *str) * @buf: buffer to build the string into * @enc: pointer to encryption info * @alias: alias to use + * @qcow: using qcow encryption * * Generate the string for id=$alias and any encryption options for * into the buffer. @@ -315,7 +316,8 @@ virQEMUBuildBufferEscapeComma(virBufferPtr buf, const char *str) * it's expected other arguments are appended after the id=$alias string. * So either turn something like: * - * "key-secret=$alias," + * "key-secret=$alias," or + * "encrypt.format=aes,encrypt.key-secret=$alias," * * or * "key-secret=$alias,cipher-alg=twofish-256,cipher-mode=cbc, @@ -325,8 +327,12 @@ virQEMUBuildBufferEscapeComma(virBufferPtr buf, const char *str) void virQEMUBuildQemuImgKeySecretOpts(virBufferPtr buf, virStorageEncryptionInfoDefPtr enc, - const char *alias) + const char *alias, + bool qcow) { + if (qcow) + virBufferAddLit(buf, "encrypt.format=aes,encrypt."); + virBufferAsprintf(buf, "key-secret=%s,", alias); if (!enc->cipher_name) diff --git a/src/util/virqemu.h b/src/util/virqemu.h index 2599481753..9a01640c6e 100644 --- a/src/util/virqemu.h +++ b/src/util/virqemu.h @@ -52,7 +52,8 @@ char *virQEMUBuildDriveCommandlineFromJSON(virJSONValuePtr src); void virQEMUBuildBufferEscapeComma(virBufferPtr buf, const char *str); void virQEMUBuildQemuImgKeySecretOpts(virBufferPtr buf, virStorageEncryptionInfoDefPtr enc, - const char *alias) + const char *alias, + bool qcow) ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_NONNULL(3); #endif /* __VIR_QEMU_H_ */ diff --git a/tests/storagevolxml2argvdata/qcow2-1.1.argv b/tests/storagevolxml2argvdata/qcow2-1.1.argv index c4dcb1bc3c..ff3d62d0a1 100644 --- a/tests/storagevolxml2argvdata/qcow2-1.1.argv +++ b/tests/storagevolxml2argvdata/qcow2-1.1.argv @@ -1,3 +1,5 @@ qemu-img create -f qcow2 -b /dev/null \ --o backing_fmt=raw,encryption=on,compat=1.1 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o backing_fmt=raw,encrypt.format=aes,\ +encrypt.key-secret=OtherDemo.img_encrypt0,compat=1.1 \ /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvdata/qcow2-compat.argv b/tests/storagevolxml2argvdata/qcow2-compat.argv index 37ad2c078d..8aa8c7ce84 100644 --- a/tests/storagevolxml2argvdata/qcow2-compat.argv +++ b/tests/storagevolxml2argvdata/qcow2-compat.argv @@ -1,3 +1,5 @@ qemu-img create -f qcow2 -b /dev/null \ --o backing_fmt=raw,encryption=on,compat=0.10 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o backing_fmt=raw,encrypt.format=aes,\ +encrypt.key-secret=OtherDemo.img_encrypt0,compat=0.10 \ /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvdata/qcow2-from-logical-compat.argv b/tests/storagevolxml2argvdata/qcow2-from-logical-compat.argv index 5f365b1f84..849c5f0218 100644 --- a/tests/storagevolxml2argvdata/qcow2-from-logical-compat.argv +++ b/tests/storagevolxml2argvdata/qcow2-from-logical-compat.argv @@ -1,3 +1,4 @@ qemu-img convert -f raw -O qcow2 \ --o encryption=on,compat=0.10 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0,compat=0.10 \ /dev/HostVG/Swap /var/lib/libvirt/images/OtherDemo.img diff --git a/tests/storagevolxml2argvdata/qcow2-lazy.argv b/tests/storagevolxml2argvdata/qcow2-lazy.argv index b7058b84cc..0c29a3fb33 100644 --- a/tests/storagevolxml2argvdata/qcow2-lazy.argv +++ b/tests/storagevolxml2argvdata/qcow2-lazy.argv @@ -1,3 +1,5 @@ qemu-img create -f qcow2 -b /dev/null \ --o backing_fmt=raw,encryption=on,compat=1.1,lazy_refcounts \ -/var/lib/libvirt/images/OtherDemo.img 5242880K +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o backing_fmt=raw,encrypt.format=aes,\ +encrypt.key-secret=OtherDemo.img_encrypt0,compat=1.1,\ +lazy_refcounts /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvdata/qcow2-nobacking-convert-prealloc-compat.argv b/tests/storagevolxml2argvdata/qcow2-nobacking-convert-prealloc-compat.argv index 3d93ec8480..a95749eafa 100644 --- a/tests/storagevolxml2argvdata/qcow2-nobacking-convert-prealloc-compat.argv +++ b/tests/storagevolxml2argvdata/qcow2-nobacking-convert-prealloc-compat.argv @@ -1,3 +1,5 @@ qemu-img convert -f raw -O qcow2 \ --o encryption=on,preallocation=metadata,compat=0.10 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0,\ +preallocation=metadata,compat=0.10 \ /var/lib/libvirt/images/sparse.img /var/lib/libvirt/images/OtherDemo.img diff --git a/tests/storagevolxml2argvdata/qcow2-nobacking-prealloc-compat.argv b/tests/storagevolxml2argvdata/qcow2-nobacking-prealloc-compat.argv index 903c94e33d..30b61442a4 100644 --- a/tests/storagevolxml2argvdata/qcow2-nobacking-prealloc-compat.argv +++ b/tests/storagevolxml2argvdata/qcow2-nobacking-prealloc-compat.argv @@ -1,3 +1,5 @@ qemu-img create -f qcow2 \ --o encryption=on,preallocation=metadata,compat=0.10 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0,\ +preallocation=metadata,compat=0.10 \ /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvdata/qcow2-nocapacity-convert-prealloc.argv b/tests/storagevolxml2argvdata/qcow2-nocapacity-convert-prealloc.argv index 73499178e7..51bdaaf684 100644 --- a/tests/storagevolxml2argvdata/qcow2-nocapacity-convert-prealloc.argv +++ b/tests/storagevolxml2argvdata/qcow2-nocapacity-convert-prealloc.argv @@ -1,4 +1,5 @@ qemu-img convert -f raw -O qcow2 \ --o encryption=on,preallocation=falloc,compat=0.10 \ -/var/lib/libvirt/images/sparse.img \ -/var/lib/libvirt/images/OtherDemo.img +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0,\ +preallocation=falloc,compat=0.10 \ +/var/lib/libvirt/images/sparse.img /var/lib/libvirt/images/OtherDemo.img diff --git a/tests/storagevolxml2argvdata/qcow2-nocapacity.argv b/tests/storagevolxml2argvdata/qcow2-nocapacity.argv index fd88055890..920cff8771 100644 --- a/tests/storagevolxml2argvdata/qcow2-nocapacity.argv +++ b/tests/storagevolxml2argvdata/qcow2-nocapacity.argv @@ -1,5 +1,7 @@ qemu-img create \ -f qcow2 \ -b /dev/null \ --o backing_fmt=raw,encryption=on,compat=0.10 \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o backing_fmt=raw,encrypt.format=aes,\ +encrypt.key-secret=OtherDemo.img_encrypt0,compat=0.10 \ /var/lib/libvirt/images/OtherDemo.img diff --git a/tests/storagevolxml2argvdata/qcow2-nocow-compat.argv b/tests/storagevolxml2argvdata/qcow2-nocow-compat.argv index d5a7547011..1c9a1a4da4 100644 --- a/tests/storagevolxml2argvdata/qcow2-nocow-compat.argv +++ b/tests/storagevolxml2argvdata/qcow2-nocow-compat.argv @@ -1,3 +1,5 @@ qemu-img create -f qcow2 -b /dev/null \ --o backing_fmt=raw,encryption=on,nocow=on,compat=0.10 \ -/var/lib/libvirt/images/OtherDemo.img 5242880K +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o backing_fmt=raw,encrypt.format=aes,\ +encrypt.key-secret=OtherDemo.img_encrypt0,nocow=on,\ +compat=0.10 /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvdata/qcow2-nocow.argv b/tests/storagevolxml2argvdata/qcow2-nocow.argv index e54801c78a..68c16f8e20 100644 --- a/tests/storagevolxml2argvdata/qcow2-nocow.argv +++ b/tests/storagevolxml2argvdata/qcow2-nocow.argv @@ -1,3 +1,4 @@ qemu-img create -f qcow2 -b /dev/null \ --o backing_fmt=raw,encryption=on,nocow=on \ +--object secret,id=OtherDemo.img_encrypt0,file=/path/to/secretFile \ +-o encrypt.format=aes,encrypt.key-secret=OtherDemo.img_encrypt0,nocow=on \ /var/lib/libvirt/images/OtherDemo.img 5242880K diff --git a/tests/storagevolxml2argvtest.c b/tests/storagevolxml2argvtest.c index 0265a0ffe2..4286c50c6e 100644 --- a/tests/storagevolxml2argvtest.c +++ b/tests/storagevolxml2argvtest.c @@ -82,7 +82,7 @@ testCompareXMLToArgvFiles(bool shouldFail, cmd = virStorageBackendCreateQemuImgCmdFromVol(obj, vol, inputvol, flags, create_tool, - NULL); + "/path/to/secretFile"); if (!cmd) { if (shouldFail) { virResetLastError(); -- 2.14.3 -- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list