Skip to content
Permalink
Browse files

Merge pull request #12545 from shenweip/UMD-switch

UMD switch: Code clean up and fix a out of range error in thread queue.
  • Loading branch information
hrydgard committed Jan 5, 2020
2 parents b0cd261 + 9be8fc6 commit 78e36ece51f6c97d356acc9732042c9effa5f100
@@ -270,30 +270,41 @@ std::string MetaFileSystem::NormalizePrefix(std::string prefix) const {
return prefix;
}

void MetaFileSystem::Mount(std::string prefix, IFileSystem *system)
{
void MetaFileSystem::Mount(std::string prefix, IFileSystem *system) {
std::lock_guard<std::recursive_mutex> guard(lock);
MountPoint x;
x.prefix = prefix;
x.system = system;
fileSystems.push_back(x);
}

void MetaFileSystem::Unmount(std::string prefix, IFileSystem *system)
{
void MetaFileSystem::Unmount(std::string prefix, IFileSystem *system) {
std::lock_guard<std::recursive_mutex> guard(lock);
MountPoint x;
x.prefix = prefix;
x.system = system;
fileSystems.erase(std::remove(fileSystems.begin(), fileSystems.end(), x), fileSystems.end());
}

void MetaFileSystem::Remount(IFileSystem *oldSystem, IFileSystem *newSystem) {
for (auto it = fileSystems.begin(); it != fileSystems.end(); ++it) {
if (it->system == oldSystem) {
it->system = newSystem;
void MetaFileSystem::Remount(std::string prefix, IFileSystem *newSystem) {
std::lock_guard<std::recursive_mutex> guard(lock);
IFileSystem *oldSystem = nullptr;
for (auto &it : fileSystems) {
if (it.prefix == prefix) {
oldSystem = it.system;
it.system = newSystem;
}
}

bool delOldSystem = true;
for (auto &it : fileSystems) {
if (it.system == oldSystem) {
delOldSystem = false;
}
}

if (delOldSystem)
delete oldSystem;
}

IFileSystem *MetaFileSystem::GetSystemFromFilename(const std::string &filename) {
@@ -52,7 +52,7 @@ class MetaFileSystem : public IHandleAllocator, public IFileSystem {

void Mount(std::string prefix, IFileSystem *system);
void Unmount(std::string prefix, IFileSystem *system);
void Remount(IFileSystem *oldSystem, IFileSystem *newSystem);
void Remount(std::string prefix, IFileSystem *newSystem);

IFileSystem *GetSystem(const std::string &prefix);
IFileSystem *GetSystemFromFilename(const std::string &filename);
@@ -1971,7 +1971,7 @@ static u32 sceIoChdir(const char *dirname) {
}

static int sceIoChangeAsyncPriority(int id, int priority) {
// priority = -1 is valid
// priority = -1 is valid,means the current thread'priority
if (priority != -1 && (priority < 0x08 || priority > 0x77)) {
return hleLogError(SCEIO, SCE_KERNEL_ERROR_ILLEGAL_PRIORITY, "illegal priority %d", priority);
}
@@ -425,7 +425,7 @@ static int sceUmdWaitDriveStatWithTimer(u32 stat, u32 timeout)
DEBUG_LOG(SCEIO, "sceUmdWaitDriveStatWithTimer(stat = %08x, timeout = %d): waiting", stat, timeout);
__UmdWaitStat(timeout);
umdWaitingThreads.push_back(__KernelGetCurThread());
__KernelWaitCurThread(WAITTYPE_UMD, 1, stat, 0, 0, "umd stat waited with timer");
__KernelWaitCurThread(WAITTYPE_UMD, 1, stat, 0, false, "umd stat waited with timer");
return 0;
} else {
hleReSchedule("umd stat checked");
@@ -495,45 +495,17 @@ static u32 sceUmdGetErrorStat()
}

void __UmdReplace(std::string filepath) {
// TODO: This should really go through Loaders, no? What if it's an invalid file?

// Only get system from disc0 seems have been enough.
IFileSystem* currentUMD = pspFileSystem.GetSystem("disc0:");
IFileSystem* currentISOBlock = pspFileSystem.GetSystem("umd0:");
if (!currentUMD)
return;

FileLoader *loadedFile = ConstructFileLoader(filepath);

IFileSystem* umd2;
if (!loadedFile->Exists()) {
delete loadedFile;
std::string error = "";
if (!UmdReplace(filepath, error)) {
ERROR_LOG(SCEIO, "UMD Replace failed: %s", error.c_str());
return;
}
UpdateLoadedFile(loadedFile);

if (loadedFile->IsDirectory()) {
umd2 = new VirtualDiscFileSystem(&pspFileSystem, filepath);
} else {
auto bd = constructBlockDevice(loadedFile);
if (!bd)
return;
umd2 = new ISOFileSystem(&pspFileSystem, bd);
pspFileSystem.Remount(currentUMD, umd2);

if (currentUMD != currentISOBlock) {
// We mounted an ISO block system separately.
IFileSystem *iso = new ISOBlockSystem(static_cast<ISOFileSystem *>(umd2));
pspFileSystem.Remount(currentISOBlock, iso);
delete currentISOBlock;
}
}
delete currentUMD;
UMDInserted = false;
CoreTiming::ScheduleEvent(usToCycles(200*1000), umdInsertChangeEvent, 0); // Wait sceUmdCheckMedium call
// TODO Is this always correct if UMD was not activated?
u32 notifyArg = PSP_UMD_PRESENT | PSP_UMD_READABLE | PSP_UMD_CHANGED;
if (driveCBId != -1)
if (driveCBId != 0)
__KernelNotifyCallback(driveCBId, notifyArg);
}

@@ -355,3 +355,41 @@ bool LoadFile(FileLoader **fileLoaderPtr, std::string *error_string) {
coreState = CORE_ERROR;
return false;
}

bool UmdReplace(std::string filepath, std::string &error) {
IFileSystem* currentUMD = pspFileSystem.GetSystem("disc0:");

if (!currentUMD) {
error = "has no disc";
return false;
}

FileLoader *loadedFile = ConstructFileLoader(filepath);

if (!loadedFile->Exists()) {
delete loadedFile;
error = loadedFile->Path() + " doesn't exist";
return false;
}
UpdateLoadedFile(loadedFile);

loadedFile = ResolveFileLoaderTarget(loadedFile);
IdentifiedFileType type = Identify_File(loadedFile);

switch (type) {
case IdentifiedFileType::PSP_ISO:
case IdentifiedFileType::PSP_ISO_NP:
case IdentifiedFileType::PSP_DISC_DIRECTORY:
if (!ReInitMemoryForGameISO(loadedFile)) {
error = "reinit memory failed";
return false;
}

break;
default:
error = "Unsupported file type:" + std::to_string((int)type);
return false;
break;
}
return true;
}
@@ -158,3 +158,5 @@ void RegisterFileLoaderFactory(std::string name, std::unique_ptr<FileLoaderFacto

// Can modify the string filename, as it calls IdentifyFile above.
bool LoadFile(FileLoader **fileLoaderPtr, std::string *error_string);

bool UmdReplace(std::string filepath, std::string &error);
@@ -83,7 +83,7 @@ void InitMemoryForGameISO(FileLoader *fileLoader) {

IFileSystem *fileSystem = nullptr;
IFileSystem *blockSystem = nullptr;
bool actualIso = false;

if (fileLoader->IsDirectory()) {
fileSystem = new VirtualDiscFileSystem(&pspFileSystem, fileLoader->Path());
blockSystem = fileSystem;
@@ -144,6 +144,35 @@ void InitMemoryForGameISO(FileLoader *fileLoader) {
}
}

bool ReInitMemoryForGameISO(FileLoader *fileLoader) {
if (!fileLoader->Exists()) {
return false;
}

IFileSystem *fileSystem = nullptr;
IFileSystem *blockSystem = nullptr;

if (fileLoader->IsDirectory()) {
fileSystem = new VirtualDiscFileSystem(&pspFileSystem, fileLoader->Path());
blockSystem = fileSystem;
} else {
auto bd = constructBlockDevice(fileLoader);
if (!bd)
return false;

ISOFileSystem *iso = new ISOFileSystem(&pspFileSystem, bd);
fileSystem = iso;
blockSystem = new ISOBlockSystem(iso);
}

pspFileSystem.Remount("umd0:", blockSystem);
pspFileSystem.Remount("umd1:", blockSystem);
pspFileSystem.Remount("umd:", blockSystem);
pspFileSystem.Remount("disc0:", fileSystem);

return true;
}

void InitMemoryForGamePBP(FileLoader *fileLoader) {
if (!fileLoader->Exists()) {
return;
@@ -25,5 +25,6 @@ bool Load_PSP_ISO(FileLoader *fileLoader, std::string *error_string);
bool Load_PSP_ELF_PBP(FileLoader *fileLoader, std::string *error_string);
bool Load_PSP_GE_Dump(FileLoader *fileLoader, std::string *error_string);
void InitMemoryForGameISO(FileLoader *fileLoader);
bool ReInitMemoryForGameISO(FileLoader *fileLoader);
void InitMemoryForGamePBP(FileLoader *fileLoader);
void PSPLoaders_Shutdown();

0 comments on commit 78e36ec

Please sign in to comment.
You can’t perform that action at this time.