fix hang when importing certain modpacks
Modified findFolderOfFileInZip to use a breadth-first search and support searching for multiple file names in one pass. This should prevent or at least make it less likely to hang while importing certain packs. Signed-off-by: Lenny McLennington <lenny@sneed.church>
This commit is contained in:
parent
b995074440
commit
e2875ef9a5
@ -164,23 +164,21 @@ void InstanceImportTask::processZipPack()
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
QString mmcRoot = MMCZip::findFolderOfFileInZip(m_packZip.get(), "instance.cfg");
|
auto [rootDirectory, fileName] = MMCZip::findFolderOfFileInZip(m_packZip.get(), {"manifest.json", "instance.cfg"});
|
||||||
QString flameRoot = MMCZip::findFolderOfFileInZip(m_packZip.get(), "manifest.json");
|
if(fileName == "manifest.json")
|
||||||
|
|
||||||
if (!mmcRoot.isNull())
|
|
||||||
{
|
|
||||||
// process as MultiMC instance/pack
|
|
||||||
qDebug() << "MultiMC:" << mmcRoot;
|
|
||||||
root = mmcRoot;
|
|
||||||
m_modpackType = ModpackType::MultiMC;
|
|
||||||
}
|
|
||||||
else if(!flameRoot.isNull())
|
|
||||||
{
|
{
|
||||||
// process as Flame pack
|
// process as Flame pack
|
||||||
qDebug() << "Flame:" << flameRoot;
|
qDebug() << "Flame:" << rootDirectory;
|
||||||
root = flameRoot;
|
root = rootDirectory;
|
||||||
m_modpackType = ModpackType::Flame;
|
m_modpackType = ModpackType::Flame;
|
||||||
}
|
}
|
||||||
|
else if (fileName == "instance.cfg")
|
||||||
|
{
|
||||||
|
// process as MultiMC instance/pack
|
||||||
|
qDebug() << "MultiMC:" << rootDirectory;
|
||||||
|
root = rootDirectory;
|
||||||
|
m_modpackType = ModpackType::MultiMC;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if(m_modpackType == ModpackType::Unknown)
|
if(m_modpackType == ModpackType::Unknown)
|
||||||
{
|
{
|
||||||
|
@ -40,6 +40,7 @@
|
|||||||
#include "FileSystem.h"
|
#include "FileSystem.h"
|
||||||
|
|
||||||
#include <QDebug>
|
#include <QDebug>
|
||||||
|
#include <deque>
|
||||||
|
|
||||||
// ours
|
// ours
|
||||||
bool MMCZip::mergeZipFiles(QuaZip *into, QFileInfo from, QSet<QString> &contained, const FilterFunction filter)
|
bool MMCZip::mergeZipFiles(QuaZip *into, QFileInfo from, QSet<QString> &contained, const FilterFunction filter)
|
||||||
@ -228,23 +229,27 @@ bool MMCZip::createModdedJar(QString sourceJarPath, QString targetJarPath, const
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ours
|
// ours
|
||||||
QString MMCZip::findFolderOfFileInZip(QuaZip * zip, const QString & what, const QString &root)
|
std::pair<QString, QString> MMCZip::findFolderOfFileInZip(QuaZip * zip, QSet<const QString> what, const QString &root)
|
||||||
{
|
{
|
||||||
QuaZipDir rootDir(zip, root);
|
std::deque<QString> pathsToTraverse;
|
||||||
for(auto fileName: rootDir.entryList(QDir::Files))
|
pathsToTraverse.push_back(root);
|
||||||
|
while (!pathsToTraverse.empty())
|
||||||
{
|
{
|
||||||
if(fileName == what)
|
QString currentPath = pathsToTraverse.front();
|
||||||
return root;
|
pathsToTraverse.pop_front();
|
||||||
}
|
QuaZipDir rootDir(zip, currentPath);
|
||||||
for(auto fileName: rootDir.entryList(QDir::Dirs))
|
|
||||||
{
|
for(auto fileName: rootDir.entryList(QDir::Files))
|
||||||
QString result = findFolderOfFileInZip(zip, what, root + fileName);
|
|
||||||
if(!result.isEmpty())
|
|
||||||
{
|
{
|
||||||
return result;
|
if (what.contains(fileName))
|
||||||
|
return {currentPath, fileName};
|
||||||
|
}
|
||||||
|
for(auto fileName: rootDir.entryList(QDir::Dirs))
|
||||||
|
{
|
||||||
|
pathsToTraverse.push_back(root);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return QString();
|
return {QString(), QString()};
|
||||||
}
|
}
|
||||||
|
|
||||||
// ours
|
// ours
|
||||||
|
@ -78,11 +78,11 @@ namespace MMCZip
|
|||||||
bool createModdedJar(QString sourceJarPath, QString targetJarPath, const QList<Mod*>& mods);
|
bool createModdedJar(QString sourceJarPath, QString targetJarPath, const QList<Mod*>& mods);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find a single file in archive by file name (not path)
|
* Breath-first find a single file in archive by a list of file names (not path)
|
||||||
*
|
*
|
||||||
* \return the path prefix where the file is
|
* \return pair of {file parent directory, file name}
|
||||||
*/
|
*/
|
||||||
QString findFolderOfFileInZip(QuaZip * zip, const QString & what, const QString &root = QString(""));
|
std::pair<QString, QString> findFolderOfFileInZip(QuaZip * zip, QSet<const QString> what, const QString &root = QString(""));
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find a multiple files of the same name in archive by file name
|
* Find a multiple files of the same name in archive by file name
|
||||||
|
@ -285,7 +285,7 @@ void World::readFromZip(const QFileInfo &file)
|
|||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
auto location = MMCZip::findFolderOfFileInZip(&zip, "level.dat");
|
auto [location, _] = MMCZip::findFolderOfFileInZip(&zip, {"level.dat"});
|
||||||
is_valid = !location.isEmpty();
|
is_valid = !location.isEmpty();
|
||||||
if (!is_valid)
|
if (!is_valid)
|
||||||
{
|
{
|
||||||
|
Loading…
Reference in New Issue
Block a user