diff --git a/Core/HLE/sceIo.cpp b/Core/HLE/sceIo.cpp index 0c4dcf20e1..c1e3f9e998 100644 --- a/Core/HLE/sceIo.cpp +++ b/Core/HLE/sceIo.cpp @@ -21,6 +21,7 @@ #include #include "Common/Thread/ThreadUtil.h" +#include "Common/TimeUtil.h" #include "Common/Profiler/Profiler.h" #include "Common/File/FileUtil.h" @@ -2321,10 +2322,48 @@ static u32 sceIoDopen(const char *path) { DirListing *dir = new DirListing(); SceUID id = kernelObjects.Create(dir); + double time = time_now_d(); dir->listing = pspFileSystem.GetDirListing(path); dir->index = 0; dir->name = std::string(path); + // Blacklist some directories that games should not be able to find out about. + // Speeds up directory iteration on slow Android Scoped Storage implementations :( + // Might also want to filter out PSP/GAME if not a homebrew, maybe also irrelevant directories + // in PSP/SAVEDATA, though iffy to know which ones are irrelevant.. + if (!strcmp(path, "ms0:/PSP")) { + static const char *const pspFolderBlacklist[] = { + "CHEATS", + "PPSSPP_STATE", + "PLUGINS", + "SYSTEM", + "SCREENSHOT", + "TEXTURES", + "DUMP", + }; + std::vector filtered; + for (const auto &entry : dir->listing) { + bool blacklisted = false; + for (auto black : pspFolderBlacklist) { + if (!strcasecmp(entry.name.c_str(), black)) { + blacklisted = true; + break; + } + } + + if (!blacklisted) { + filtered.push_back(entry); + } + } + + dir->listing = filtered; + } + + double diff = time_now_d() - time; + //if (diff > 0.01) { + ERROR_LOG(IO, "sceIoDopen(%s) took %0.3f seconds", path, diff); + //} + // TODO: The result is delayed only from the memstick, it seems. return id; } @@ -2349,7 +2388,7 @@ static u32 sceIoDread(int id, u32 dirent_addr) { SceIoDirEnt *entry = (SceIoDirEnt*) Memory::GetPointer(dirent_addr); if (dir->index == (int) dir->listing.size()) { - DEBUG_LOG(SCEIO, "sceIoDread( %d %08x ) - end of the line", id, dirent_addr); + DEBUG_LOG(SCEIO, "sceIoDread( %d %08x ) - end", id, dirent_addr); entry->d_name[0] = '\0'; return 0; }