diff --git a/src/core/file_sys/card_image.cpp b/src/core/file_sys/card_image.cpp index 395eea8ae0bf37d80a6795a6cc97c7aeaae9ca87..e897d99130f6f74a39dd379be3dd24066902358a 100644 --- a/src/core/file_sys/card_image.cpp +++ b/src/core/file_sys/card_image.cpp @@ -5,6 +5,7 @@ #include <array> #include <string> #include <core/loader/loader.h> +#include "common/logging/log.h" #include "core/file_sys/card_image.h" #include "core/file_sys/partition_filesystem.h" #include "core/file_sys/vfs_offset.h" diff --git a/src/core/file_sys/content_archive.cpp b/src/core/file_sys/content_archive.cpp index 79e70f6ef13abddcf4fbd2f25395250ef4626bce..8cd1f5e6ac97229df3df7847bd4a178b8377c9f3 100644 --- a/src/core/file_sys/content_archive.cpp +++ b/src/core/file_sys/content_archive.cpp @@ -140,6 +140,10 @@ VirtualFile NCA::Decrypt(NCASectionHeader header, VirtualFile in, u64 starting_o } NCA::NCA(VirtualFile file_) : file(std::move(file_)) { + if (file == nullptr) { + status = Loader::ResultStatus::ErrorInvalidFormat; + return; + } if (sizeof(NCAHeader) != file->ReadObject(&header)) LOG_ERROR(Loader, "File reader errored out during header read."); diff --git a/src/core/file_sys/content_archive.h b/src/core/file_sys/content_archive.h index 6492163b53318d28ac0c9b528078eef9b33cc65c..a984a4d3613122a6f3dea55fc59f71cd988ed659 100644 --- a/src/core/file_sys/content_archive.h +++ b/src/core/file_sys/content_archive.h @@ -12,6 +12,7 @@ #include "common/common_funcs.h" #include "common/common_types.h" #include "common/swap.h" +#include "control_metadata.h" #include "core/crypto/key_manager.h" #include "core/file_sys/partition_filesystem.h" #include "core/loader/loader.h" diff --git a/src/core/loader/nca.h b/src/core/loader/nca.h index 443bc1202494b4d3d66826df222d30774cf58f2c..7f7d8ea0ba4891b8deb2e584bc0ce8f259a43626 100644 --- a/src/core/loader/nca.h +++ b/src/core/loader/nca.h @@ -35,8 +35,6 @@ public: ResultStatus ReadRomFS(FileSys::VirtualFile& dir) override; ResultStatus ReadProgramId(u64& out_program_id) override; - ResultStatus ReadProgramId(u64& out_program_id) override; - ~AppLoader_NCA(); private: diff --git a/src/core/loader/xci.cpp b/src/core/loader/xci.cpp index eb4dee2c259a4adc117cb04df2ee9cb9cc05cdaf..d3fe24419ac9a4783428fc44fe557e63d7519a43 100644 --- a/src/core/loader/xci.cpp +++ b/src/core/loader/xci.cpp @@ -26,7 +26,25 @@ namespace Loader { AppLoader_XCI::AppLoader_XCI(FileSys::VirtualFile file) : AppLoader(file), xci(std::make_unique<FileSys::XCI>(file)), nca_loader(std::make_unique<AppLoader_NCA>( - xci->GetNCAFileByType(FileSys::NCAContentType::Program))) {} + xci->GetNCAFileByType(FileSys::NCAContentType::Program))) { + if (xci->GetStatus() != ResultStatus::Success) + return; + const auto control_nca = xci->GetNCAByType(FileSys::NCAContentType::Control); + if (control_nca == nullptr || control_nca->GetStatus() != ResultStatus::Success) + return; + const auto romfs = FileSys::ExtractRomFS(control_nca->GetRomFS()); + if (romfs == nullptr) + return; + for (const auto& language : FileSys::LANGUAGE_NAMES) { + icon_file = romfs->GetFile("icon_" + std::string(language) + ".dat"); + if (icon_file != nullptr) + break; + } + const auto nacp_raw = romfs->GetFile("control.nacp"); + if (nacp_raw == nullptr) + return; + nacp_file = std::make_shared<FileSys::NACP>(nacp_raw); +} AppLoader_XCI::~AppLoader_XCI() = default; @@ -71,4 +89,17 @@ ResultStatus AppLoader_XCI::ReadProgramId(u64& out_program_id) { return nca_loader->ReadProgramId(out_program_id); } +ResultStatus AppLoader_XCI::ReadIcon(std::vector<u8>& buffer) { + if (icon_file == nullptr) + return ResultStatus::ErrorInvalidFormat; + buffer = icon_file->ReadAllBytes(); + return ResultStatus::Success; +} + +ResultStatus AppLoader_XCI::ReadTitle(std::string& title) { + if (nacp_file == nullptr) + return ResultStatus::ErrorInvalidFormat; + title = nacp_file->GetApplicationName(); + return ResultStatus::Success; +} } // namespace Loader diff --git a/src/core/loader/xci.h b/src/core/loader/xci.h index 0dbcfbdf83d74bc0d2f37268a62dc2287c9f36c0..973833050e5c1c3972b1626edfa9c66aea7a8918 100644 --- a/src/core/loader/xci.h +++ b/src/core/loader/xci.h @@ -33,12 +33,17 @@ public: ResultStatus ReadRomFS(FileSys::VirtualFile& dir) override; ResultStatus ReadProgramId(u64& out_program_id) override; + ResultStatus ReadIcon(std::vector<u8>& buffer) override; + ResultStatus ReadTitle(std::string& title) override; private: FileSys::ProgramMetadata metadata; std::unique_ptr<FileSys::XCI> xci; std::unique_ptr<AppLoader_NCA> nca_loader; + + FileSys::VirtualFile icon_file; + std::shared_ptr<FileSys::NACP> nacp_file; }; } // namespace Loader diff --git a/src/yuzu/game_list.cpp b/src/yuzu/game_list.cpp index 481d91be58349c0c2ee7f81e62f12d6ecbf6df48..5f47f5a2ba7887dd05ea830dc9ae3c72d9c5b12e 100644 --- a/src/yuzu/game_list.cpp +++ b/src/yuzu/game_list.cpp @@ -9,6 +9,7 @@ #include <QKeyEvent> #include <QMenu> #include <QThreadPool> +#include <boost/container/flat_map.hpp> #include "common/common_paths.h" #include "common/logging/log.h" #include "common/string_util.h" @@ -458,9 +459,9 @@ void GameListWorker::AddFstEntriesToGameList(const std::string& dir_path, unsign // Use from metadata pool. if (nca_control_map.find(program_id) != nca_control_map.end()) { const auto nca = nca_control_map[program_id]; - auto control_dir = nca->GetSection(0); + const auto control_dir = nca->GetSubdirectories()[0]; - auto nacp_file = control_dir->GetFile("control.nacp"); + const auto nacp_file = control_dir->GetFile("control.nacp"); FileSys::NACP nacp(nacp_file); name = nacp.GetApplicationName();