From 46f5d5eeb3b1d0586106b33cecf600ab66170b45 Mon Sep 17 00:00:00 2001 From: Ingo Klöcker Date: Fri, 27 Oct 2023 16:07:16 +0200 Subject: qt: Use temporary .part file names when creating archives * lang/qt/src/util.h, lang/qt/src/util.cpp (class PartialFileGuard): New. * lang/qt/src/util.cpp (getRandomCharacters, createPartFileName): New. * lang/qt/src/qgpgmeencryptarchivejob.cpp (encrypt_to_filename): Use PartialFileGuard. * lang/qt/src/qgpgmesignarchivejob.cpp (sign_to_filename): Ditto. * lang/qt/src/qgpgmesignencryptarchivejob.cpp (sign_encrypt_to_filename): Ditto. -- When creating signed and/or encrypted archives, gpgtar now writes the result to a temporary file name. On success, the archive is renamed to the final file name. Otherwise, the (partially written) temporary file is removed (if possible). GnuPG-bug-id: 6721 --- lang/qt/src/qgpgmesignarchivejob.cpp | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'lang/qt/src/qgpgmesignarchivejob.cpp') diff --git a/lang/qt/src/qgpgmesignarchivejob.cpp b/lang/qt/src/qgpgmesignarchivejob.cpp index fc36d886..4a0e1f7f 100644 --- a/lang/qt/src/qgpgmesignarchivejob.cpp +++ b/lang/qt/src/qgpgmesignarchivejob.cpp @@ -138,18 +138,23 @@ static QGpgMESignArchiveJob::result_type sign_to_filename(Context *ctx, const QString &outputFileName, const QString &baseDirectory) { + PartialFileGuard partFileGuard{outputFileName}; + if (partFileGuard.tempFileName().isEmpty()) { + return std::make_tuple(SigningResult{Error::fromCode(GPG_ERR_EEXIST)}, QString{}, Error{}); + } + Data outdata; #ifdef Q_OS_WIN - outdata.setFileName(outputFileName.toUtf8().constData()); + outdata.setFileName(partFileGuard.tempFileName().toUtf8().constData()); #else - outdata.setFileName(QFile::encodeName(outputFileName).constData()); + outdata.setFileName(QFile::encodeName(partFileGuard.tempFileName()).constData()); #endif const auto result = sign(ctx, signers, paths, outdata, baseDirectory); const auto &signingResult = std::get<0>(result); - if (signingResult.error().code()) { - // ensure that the output file is removed if the operation was canceled or failed - removeFile(outputFileName); + if (!signingResult.error().code()) { + // the operation succeeded -> save the result under the requested file name + partFileGuard.commit(); } return result; -- cgit