Blame SOURCES/kvm-crypto.c-cleanup-created-file-when-block_crypto_co_c.patch

77c23f
From 043decff5812c1f46ed44dd0f82099e3b8bb6a28 Mon Sep 17 00:00:00 2001
77c23f
From: Maxim Levitsky <mlevitsk@redhat.com>
77c23f
Date: Sun, 31 May 2020 16:40:35 +0100
77c23f
Subject: [PATCH 7/7] crypto.c: cleanup created file when
77c23f
 block_crypto_co_create_opts_luks fails
77c23f
77c23f
RH-Author: Maxim Levitsky <mlevitsk@redhat.com>
77c23f
Message-id: <20200531164035.34188-4-mlevitsk@redhat.com>
77c23f
Patchwork-id: 97060
77c23f
O-Subject: [RHEL-AV-8.2.1 qemu-kvm PATCH 3/3] crypto.c: cleanup created file when block_crypto_co_create_opts_luks fails
77c23f
Bugzilla: 1827630
77c23f
RH-Acked-by: Sergio Lopez Pascual <slp@redhat.com>
77c23f
RH-Acked-by: John Snow <jsnow@redhat.com>
77c23f
RH-Acked-by: Eric Blake <eblake@redhat.com>
77c23f
77c23f
From: Daniel Henrique Barboza <danielhb413@gmail.com>
77c23f
77c23f
When using a non-UTF8 secret to create a volume using qemu-img, the
77c23f
following error happens:
77c23f
77c23f
$ qemu-img create -f luks --object secret,id=vol_1_encrypt0,file=vol_resize_pool.vol_1.secret.qzVQrI -o key-secret=vol_1_encrypt0 /var/tmp/pool_target/vol_1 10240K
77c23f
77c23f
Formatting '/var/tmp/pool_target/vol_1', fmt=luks size=10485760 key-secret=vol_1_encrypt0
77c23f
qemu-img: /var/tmp/pool_target/vol_1: Data from secret vol_1_encrypt0 is not valid UTF-8
77c23f
77c23f
However, the created file '/var/tmp/pool_target/vol_1' is left behind in the
77c23f
file system after the failure. This behavior can be observed when creating
77c23f
the volume using Libvirt, via 'virsh vol-create', and then getting "volume
77c23f
target path already exist" errors when trying to re-create the volume.
77c23f
77c23f
The volume file is created inside block_crypto_co_create_opts_luks(), in
77c23f
block/crypto.c. If the bdrv_create_file() call is successful but any
77c23f
succeeding step fails*, the existing 'fail' label does not take into
77c23f
account the created file, leaving it behind.
77c23f
77c23f
This patch changes block_crypto_co_create_opts_luks() to delete
77c23f
'filename' in case of failure. A failure in this point means that
77c23f
the volume is now truncated/corrupted, so even if 'filename' was an
77c23f
existing volume before calling qemu-img, it is now unusable. Deleting
77c23f
the file it is not much worse than leaving it in the filesystem in
77c23f
this scenario, and we don't have to deal with checking the file
77c23f
pre-existence in the code.
77c23f
77c23f
* in our case, block_crypto_co_create_generic calls qcrypto_block_create,
77c23f
which calls qcrypto_block_luks_create, and this function fails when
77c23f
calling qcrypto_secret_lookup_as_utf8.
77c23f
77c23f
Reported-by: Srikanth Aithal <bssrikanth@in.ibm.com>
77c23f
Suggested-by: Kevin Wolf <kwolf@redhat.com>
77c23f
Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com>
77c23f
Message-Id: <20200130213907.2830642-4-danielhb413@gmail.com>
77c23f
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
77c23f
(cherry picked from commit 1bba30da24e1124ceeb0693c81382a0d77e20ca5)
77c23f
Signed-off-by: Maxim Levitsky <mlevitsk@redhat.com>
77c23f
Signed-off-by: Danilo C. L. de Paula <ddepaula@redhat.com>
77c23f
---
77c23f
 block/crypto.c | 18 ++++++++++++++++++
77c23f
 1 file changed, 18 insertions(+)
77c23f
77c23f
diff --git a/block/crypto.c b/block/crypto.c
77c23f
index 970d463..5e3b15c 100644
77c23f
--- a/block/crypto.c
77c23f
+++ b/block/crypto.c
77c23f
@@ -30,6 +30,7 @@
77c23f
 #include "qapi/error.h"
77c23f
 #include "qemu/module.h"
77c23f
 #include "qemu/option.h"
77c23f
+#include "qemu/cutils.h"
77c23f
 #include "crypto.h"
77c23f
 
77c23f
 typedef struct BlockCrypto BlockCrypto;
77c23f
@@ -597,6 +598,23 @@ static int coroutine_fn block_crypto_co_create_opts_luks(BlockDriver *drv,
77c23f
 
77c23f
     ret = 0;
77c23f
 fail:
77c23f
+    /*
77c23f
+     * If an error occurred, delete 'filename'. Even if the file existed
77c23f
+     * beforehand, it has been truncated and corrupted in the process.
77c23f
+     */
77c23f
+    if (ret && bs) {
77c23f
+        Error *local_delete_err = NULL;
77c23f
+        int r_del = bdrv_co_delete_file(bs, &local_delete_err);
77c23f
+        /*
77c23f
+         * ENOTSUP will happen if the block driver doesn't support
77c23f
+         * the 'bdrv_co_delete_file' interface. This is a predictable
77c23f
+         * scenario and shouldn't be reported back to the user.
77c23f
+         */
77c23f
+        if ((r_del < 0) && (r_del != -ENOTSUP)) {
77c23f
+            error_report_err(local_delete_err);
77c23f
+        }
77c23f
+    }
77c23f
+
77c23f
     bdrv_unref(bs);
77c23f
     qapi_free_QCryptoBlockCreateOptions(create_opts);
77c23f
     qobject_unref(cryptoopts);
77c23f
-- 
77c23f
1.8.3.1
77c23f