From 2e510e5ca0ed9c6376a5db7d136bbc0b8fdbce9a Mon Sep 17 00:00:00 2001 From: Nekotekina Date: Sun, 3 Sep 2017 22:29:20 +0300 Subject: [PATCH] Fix rXml limitation (trophies) --- Utilities/rXml.cpp | 5 ++- Utilities/rXml.h | 2 +- rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp | 50 +++++++++++++++----------- rpcs3/Loader/TROPUSR.cpp | 11 +++--- 4 files changed, 39 insertions(+), 29 deletions(-) diff --git a/Utilities/rXml.cpp b/Utilities/rXml.cpp index be52679cd6..3505d1b056 100644 --- a/Utilities/rXml.cpp +++ b/Utilities/rXml.cpp @@ -61,10 +61,9 @@ rXmlDocument::rXmlDocument() : handle() { } -void rXmlDocument::Load(const std::string & path) +void rXmlDocument::Read(const std::string& data) { - // TODO: Unsure of use of c_str. - handle.load_file(path.c_str()); + handle.load_buffer(data.data(), data.size()); } std::shared_ptr rXmlDocument::GetRoot() diff --git a/Utilities/rXml.h b/Utilities/rXml.h index c2abcfef0e..704801fab7 100644 --- a/Utilities/rXml.h +++ b/Utilities/rXml.h @@ -24,7 +24,7 @@ struct rXmlDocument rXmlDocument(); rXmlDocument(const rXmlDocument& other) = delete; rXmlDocument &operator=(const rXmlDocument& other) = delete; - void Load(const std::string & path); + void Read(const std::string& data); std::shared_ptr GetRoot(); pugi::xml_document handle; diff --git a/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp b/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp index acc9ae0547..d69a6ad143 100644 --- a/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp +++ b/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp @@ -398,12 +398,15 @@ error_code sceNpTrophyGetGameInfo(u32 context, u32 handle, vm::ptrtrp_name + "/TROPCONF.SFM"); + fs::file config(vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + "/TROPCONF.SFM")); + + if (!config) + { + return SCE_NP_TROPHY_ERROR_CONF_DOES_NOT_EXIST; + } - // TODO: rXmlDocument can open only real file - verify(HERE), !fs::get_virtual_device(path); rXmlDocument doc; - doc.Load(path); + doc.Read(config.to_string()); for (std::shared_ptr n = doc.GetRoot()->GetChildren(); n; n = n->GetNext()) { @@ -551,12 +554,16 @@ error_code sceNpTrophyGetTrophyInfo(u32 context, u32 handle, s32 trophyId, vm::p } // TODO: Get the path of the current user - const std::string& path = vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + "/TROPCONF.SFM"); + fs::file config(vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + "/TROPCONF.SFM")); + + if (!config) + { + return SCE_NP_TROPHY_ERROR_CONF_DOES_NOT_EXIST; + } - // TODO: rXmlDocument can open only real file - verify(HERE), !fs::get_virtual_device(path); rXmlDocument doc; - doc.Load(path); + doc.Read(config.to_string()); + auto trophy_base = doc.GetRoot(); if (trophy_base->GetChildren()->GetName() == "trophyconf") { @@ -564,7 +571,8 @@ error_code sceNpTrophyGetTrophyInfo(u32 context, u32 handle, s32 trophyId, vm::p } bool found = false; - for (std::shared_ptr n = trophy_base->GetChildren(); n; n = n->GetNext()) { + for (std::shared_ptr n = trophy_base->GetChildren(); n; n = n->GetNext()) + { if (n->GetName() == "trophy" && (trophyId == atoi(n->GetAttribute("id").c_str()))) { found = true; @@ -681,21 +689,21 @@ error_code sceNpTrophyGetGameIcon(u32 context, u32 handle, vm::ptr buffer, return SCE_NP_TROPHY_ERROR_UNKNOWN_HANDLE; } - const std::string& path = vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + "/ICON0.PNG"); + fs::file icon_file(vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + "/ICON0.PNG")); - if (!fs::exists(path)) + if (!icon_file) { return SCE_NP_TROPHY_ERROR_UNKNOWN_FILE; } - fs::file gameIconFile(path); + const u32 icon_size = ::size32(icon_file); - if (buffer && *size >= gameIconFile.size()) + if (buffer && *size >= icon_size) { - gameIconFile.read(buffer.get_ptr(), gameIconFile.size()); + icon_file.read(buffer.get_ptr(), icon_size); } - *size = gameIconFile.size(); + *size = icon_size; return CELL_OK; } @@ -734,21 +742,21 @@ error_code sceNpTrophyGetTrophyIcon(u32 context, u32 handle, s32 trophyId, vm::p return hidden ? SCE_NP_TROPHY_ERROR_HIDDEN : SCE_NP_TROPHY_ERROR_LOCKED; } - const std::string& path = vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + fmt::format("/TROP%03d.PNG", trophyId)); + fs::file icon_file(vfs::get("/dev_hdd0/home/00000001/trophy/" + ctxt->trp_name + fmt::format("/TROP%03d.PNG", trophyId))); - if (!fs::exists(path)) + if (!icon_file) { return SCE_NP_TROPHY_ERROR_UNKNOWN_FILE; } - fs::file trophyIconFile(path); + const u32 icon_size = ::size32(icon_file); - if (buffer && *size >= trophyIconFile.size()) + if (buffer && *size >= icon_size) { - trophyIconFile.read(buffer.get_ptr(), trophyIconFile.size()); + icon_file.read(buffer.get_ptr(), icon_size); } - *size = trophyIconFile.size(); + *size = icon_size; return CELL_OK; } diff --git a/rpcs3/Loader/TROPUSR.cpp b/rpcs3/Loader/TROPUSR.cpp index fb503d8d3f..143a0c6f69 100644 --- a/rpcs3/Loader/TROPUSR.cpp +++ b/rpcs3/Loader/TROPUSR.cpp @@ -137,12 +137,15 @@ bool TROPUSRLoader::Save(const std::string& filepath) bool TROPUSRLoader::Generate(const std::string& filepath, const std::string& configpath) { - const std::string& path = vfs::get(configpath); + fs::file config(vfs::get(configpath)); + + if (!config) + { + return false; + } - // TODO: rXmlDocument can open only real file - verify(HERE), !fs::get_virtual_device(path); rXmlDocument doc; - doc.Load(path); + doc.Read(config.to_string()); m_table4.clear(); m_table6.clear();