diff --git a/plugins/CMakeLists.txt b/plugins/CMakeLists.txt --- a/plugins/CMakeLists.txt +++ b/plugins/CMakeLists.txt @@ -11,7 +11,9 @@ add_subdirectory( clizipplugin ) add_subdirectory( libsinglefileplugin ) add_subdirectory(cliunarchiverplugin) -add_subdirectory(libzipplugin) +if(LibZip_FOUND) + add_subdirectory(libzipplugin) +endif(LibZip_FOUND) set(SUPPORTED_ARK_MIMETYPES "${SUPPORTED_ARK_MIMETYPES}" PARENT_SCOPE) set(INSTALLED_KERFUFFLE_PLUGINS "${INSTALLED_KERFUFFLE_PLUGINS}" PARENT_SCOPE) diff --git a/plugins/libzipplugin/libzipplugin.h b/plugins/libzipplugin/libzipplugin.h --- a/plugins/libzipplugin/libzipplugin.h +++ b/plugins/libzipplugin/libzipplugin.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 Ragnar Thomsen + * Copyright (c) 2017 Ragnar Thomsen * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -57,10 +57,10 @@ bool emitEntryForIndex(zip_t *archive, qlonglong index); void progressEmitted(double pct); - bool m_abortOperation; + QVector m_emittedEntries; bool m_overwriteAll; bool m_skipAll; - bool m_listAfterAdd = false; + bool m_listAfterAdd; }; #endif // LIBZIPPLUGIN_H diff --git a/plugins/libzipplugin/libzipplugin.cpp b/plugins/libzipplugin/libzipplugin.cpp --- a/plugins/libzipplugin/libzipplugin.cpp +++ b/plugins/libzipplugin/libzipplugin.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 Ragnar Thomsen + * Copyright (c) 2017 Ragnar Thomsen * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -35,6 +35,7 @@ #include #include #include +#include K_PLUGIN_FACTORY_WITH_JSON(LibZipPluginFactory, "kerfuffle_libzip.json", registerPlugin();) @@ -54,27 +55,32 @@ LibzipPlugin::LibzipPlugin(QObject *parent, const QVariantList & args) : ReadWriteArchiveInterface(parent, args) - , m_abortOperation(false) + , m_overwriteAll(false) + , m_skipAll(false) + , m_listAfterAdd(false) { qCDebug(ARK) << "Initializing libzip plugin"; } LibzipPlugin::~LibzipPlugin() { + foreach (const auto e, m_emittedEntries) { + // Entries might be passed to pending slots, so we just schedule their deletion. + e->deleteLater(); + } } bool LibzipPlugin::list() { qCDebug(ARK) << "Listing archive contents for:" << QFile::encodeName(filename()); m_numberOfEntries = 0; - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), ZIP_RDONLY, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), ZIP_RDONLY, &errcode); zip_error_init_with_code(&err, errcode); if (!archive) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -92,7 +98,7 @@ // Loop through all archive entries. for (int i = 0; i < nofEntries; i++) { - if (m_abortOperation) { + if (QThread::currentThread()->isInterruptionRequested()) { break; } @@ -104,7 +110,6 @@ emit progress(float(i + 1) / nofEntries); } } - m_abortOperation = false; zip_close(archive); m_listAfterAdd = false; @@ -115,12 +120,11 @@ { Q_UNUSED(numberOfEntriesToAdd) - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), ZIP_CREATE, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), ZIP_CREATE, &errcode); zip_error_init_with_code(&err, errcode); if (!archive) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -131,7 +135,7 @@ uint i = 0; foreach (const Archive::Entry* e, files) { - if (m_abortOperation) { + if (QThread::currentThread()->isInterruptionRequested()) { break; } @@ -147,7 +151,7 @@ QDir::Hidden | QDir::NoDotAndDotDot, QDirIterator::Subdirectories); - while (!m_abortOperation && it.hasNext()) { + while (!QThread::currentThread()->isInterruptionRequested() && it.hasNext()) { QString path = it.next(); if (QFileInfo(path).isDir()) { @@ -169,7 +173,6 @@ i++; } qCDebug(ARK) << "Added" << i << "entries"; - m_abortOperation = false; // Register the callback function to get progress feedback. Callback::func = std::bind(&LibzipPlugin::progressEmitted, this, std::placeholders::_1); @@ -325,18 +328,18 @@ } emit entry(e); + m_emittedEntries << e; return true; } bool LibzipPlugin::deleteFiles(const QVector &files) { - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), 0, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), 0, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -347,7 +350,7 @@ qulonglong i = 0; foreach (const Archive::Entry* e, files) { - if (m_abortOperation) { + if (QThread::currentThread()->isInterruptionRequested()) { break; } @@ -366,7 +369,6 @@ emit progress(float(++i) / files.size()); } qCDebug(ARK) << "Deleted" << i << "entries"; - m_abortOperation = false; if (zip_close(archive)) { qCCritical(ARK) << "Failed to write archive"; @@ -378,12 +380,11 @@ bool LibzipPlugin::addComment(const QString& comment) { - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), 0, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), 0, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -409,12 +410,11 @@ { qCDebug(ARK) << "Testing archive"; - zip_t *archive; int errcode; zip_error_t err; // Open archive performing extra consistency checks. - archive = zip_open(QFile::encodeName(filename()), ZIP_CHECKCONS, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), ZIP_CHECKCONS, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive:" << zip_error_strerror(&err); @@ -429,7 +429,6 @@ bool LibzipPlugin::doKill() { qCDebug(ARK) << "Killing operation..."; - m_abortOperation = true; return true; } @@ -440,12 +439,11 @@ const bool extractAll = files.isEmpty(); const bool removeRootNode = options.isDragAndDropEnabled(); - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), ZIP_RDONLY, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), ZIP_RDONLY, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -469,7 +467,7 @@ if (extractAll) { // We extract all entries. for (qlonglong i = 0; i < nofEntries; i++) { - if (m_abortOperation) { + if (QThread::currentThread()->isInterruptionRequested()) { break; } if (!extractEntry(archive, @@ -487,7 +485,7 @@ // We extract only the entries in files. qulonglong i = 0; foreach (const Archive::Entry* e, files) { - if (m_abortOperation) { + if (QThread::currentThread()->isInterruptionRequested()) { break; } if (!extractEntry(archive, @@ -502,7 +500,6 @@ emit progress(float(++i) / nofEntries); } } - m_abortOperation = false; zip_close(archive); return true; @@ -578,7 +575,7 @@ } // Handle password-protected files. - zip_file *zf = NULL; + zip_file *zf = nullptr; bool firstTry = true; while (!zf) { zf = zip_fopen(archive, entry.toUtf8(), 0); @@ -649,12 +646,11 @@ { Q_UNUSED(options) - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), 0, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), 0, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode; @@ -700,12 +696,11 @@ { Q_UNUSED(options) - zip_t *archive; int errcode; zip_error_t err; // Open archive. - archive = zip_open(QFile::encodeName(filename()), 0, &errcode); + zip_t *archive = zip_open(QFile::encodeName(filename()), 0, &errcode); zip_error_init_with_code(&err, errcode); if (archive == NULL) { qCCritical(ARK) << "Failed to open archive. Code:" << errcode;