From 29244f3328cdf878ac557acbbabb19a5b7190b2d Mon Sep 17 00:00:00 2001 From: isanae <14251494+isanae@users.noreply.github.com> Date: Thu, 13 Feb 2020 20:13:37 -0500 Subject: thread-safe directory entry --- src/directoryrefresher.cpp | 113 ++++++++++++++++++++++++++++----------------- 1 file changed, 71 insertions(+), 42 deletions(-) (limited to 'src/directoryrefresher.cpp') diff --git a/src/directoryrefresher.cpp b/src/directoryrefresher.cpp index 5bff9d37..bce3f65a 100644 --- a/src/directoryrefresher.cpp +++ b/src/directoryrefresher.cpp @@ -25,6 +25,7 @@ along with Mod Organizer. If not, see . #include "modinfo.h" #include "settings.h" #include "envfs.h" +#include "modinfodialogfwd.h" #include #include @@ -125,7 +126,10 @@ void DirectoryRefresher::stealModFilesIntoStructure( // instead of adding all the files of the target directory, we just change the root of the specified // files to this mod - FilesOrigin &origin = directoryStructure->createOrigin(ToWString(modName), directoryW, priority); + DirectoryStats dummy; + FilesOrigin &origin = directoryStructure->createOrigin( + ToWString(modName), directoryW, priority, dummy); + for (const QString &filename : stealFiles) { if (filename.isEmpty()) { log::warn("Trying to find file with no name"); @@ -189,8 +193,12 @@ void DirectoryRefresher::addModToStructure(DirectoryEntry *directoryStructure struct ModThread { + DirectoryEntry* ds = nullptr; + std::wstring modName; std::wstring path; + int prio = -1; env::Directory* dir = nullptr; + std::condition_variable cv; std::mutex mutex; bool ready = false; @@ -206,7 +214,16 @@ struct ModThread std::unique_lock lock(mutex); cv.wait(lock, [&]{ return ready; }); - *dir = env::getFilesAndDirs(path); + ds->addFromOrigin(modName, path, prio); + + /*if (Settings::instance().archiveParsing()) { + addModBSAToStructure( + directoryStructure, + entries[i].modName, + prio, + entries[i].absolutePath, + entries[i].archives); + }*/ ready = false; } @@ -216,65 +233,75 @@ void DirectoryRefresher::addMultipleModsFilesToStructure( MOShared::DirectoryEntry *directoryStructure, const std::vector& entries, bool emitProgress) { - TimeThis tt(QString("add %1 mods").arg(entries.size())); - - env::ThreadPool threads(m_threadCount); std::vector dirs(entries.size()); - for (std::size_t i=0; i(i + 1); + { + TimeThis tt("walk dirs"); - try { - if (e.stealFiles.length() > 0) { - stealModFilesIntoStructure( - directoryStructure, e.modName, prio, e.absolutePath, e.stealFiles); - } else { - auto& mt = threads.request(); + env::ThreadPool threads(m_threadCount); - mt.path = QDir::toNativeSeparators(e.absolutePath).toStdWString(); - mt.dir = &dirs[i]; + for (std::size_t i=0; i(i + 1); - mt.wakeup(); + try + { + if (e.stealFiles.length() > 0) { + stealModFilesIntoStructure( + directoryStructure, e.modName, prio, e.absolutePath, e.stealFiles); + } else { + auto& mt = threads.request(); + + mt.ds = directoryStructure; + mt.modName = entries[i].modName.toStdWString(); + mt.path = QDir::toNativeSeparators(e.absolutePath).toStdWString(); + mt.prio = prio; + mt.dir = &dirs[i]; + + mt.wakeup(); + } + } catch (const std::exception& ex) { + emit error(tr("failed to read mod (%1): %2").arg(e.modName, ex.what())); } - } catch (const std::exception& ex) { - emit error(tr("failed to read mod (%1): %2").arg(e.modName, ex.what())); - } - if (emitProgress) { - emit progress((static_cast(i) * 100) / static_cast(entries.size()) + 1); + if (emitProgress) { + emit progress((static_cast(i) * 100) / static_cast(entries.size()) + 1); + } } - } - - threads.join(); - - for (std::size_t i=0; i(i + 1); - - directoryStructure->addFromList( - entries[i].modName.toStdWString(), - entries[i].absolutePath.toStdWString(), - dirs[i], - prio); - if (Settings::instance().archiveParsing()) { - addModBSAToStructure( - directoryStructure, - entries[i].modName, - prio, - entries[i].absolutePath, - entries[i].archives); - } + threads.join(); } + + //std::sort(stats.begin(), stats.end(), [](auto&& a, auto&& b){ + // return (naturalCompare(QString::fromStdString(a.mod), QString::fromStdString(b.mod)) < 0); + //}); + + //static int run = 1; + // + //std::ofstream out("c:\\tmp\\data.csv", std::ios::app); + + //out << fmt::format("what,run,{}", DirectoryStats::csvHeader()); + // + //for (std::size_t i=0; i