From b870202ad5d2cdf875b6c02163d1a32a5772414d Mon Sep 17 00:00:00 2001 From: bunnei Date: Sat, 20 Jan 2018 14:59:17 -0500 Subject: loader: Add DeconstructedRomDirectory for game dumps. --- src/core/loader/deconstructed_rom_directory.cpp | 101 ++++++++++++++++++++++++ 1 file changed, 101 insertions(+) create mode 100644 src/core/loader/deconstructed_rom_directory.cpp (limited to 'src/core/loader/deconstructed_rom_directory.cpp') diff --git a/src/core/loader/deconstructed_rom_directory.cpp b/src/core/loader/deconstructed_rom_directory.cpp new file mode 100644 index 0000000000..daedeaab09 --- /dev/null +++ b/src/core/loader/deconstructed_rom_directory.cpp @@ -0,0 +1,101 @@ +// Copyright 2018 yuzu emulator team +// Licensed under GPLv2 or any later version +// Refer to the license.txt file included. + +#include "common/common_funcs.h" +#include "common/common_paths.h" +#include "common/logging/log.h" +#include "common/string_util.h" +#include "core/hle/kernel/process.h" +#include "core/hle/kernel/resource_limit.h" +#include "core/loader/deconstructed_rom_directory.h" +#include "core/loader/nso.h" +#include "core/memory.h" + +namespace Loader { + +FileType AppLoader_DeconstructedRomDirectory::IdentifyType(FileUtil::IOFile& file, + const std::string& filepath) { + bool is_main_found{}; + bool is_rtld_found{}; + bool is_sdk_found{}; + + const auto callback = [&](unsigned* num_entries_out, const std::string& directory, + const std::string& virtual_name) -> bool { + + // Skip directories + std::string physical_name = directory + virtual_name; + if (FileUtil::IsDirectory(physical_name)) { + return true; + } + + // Verify filename + if (Common::ToLower(virtual_name) == "main") { + is_main_found = true; + } else if (Common::ToLower(virtual_name) == "rtld") { + is_rtld_found = true; + } else if (Common::ToLower(virtual_name) == "sdk") { + is_sdk_found = true; + } else { + // Contrinue searching + return true; + } + + // Verify file is an NSO + FileUtil::IOFile file(physical_name, "rb"); + if (AppLoader_NSO::IdentifyType(file, physical_name) != FileType::NSO) { + return false; + } + + // We are done if we've found and verified all required NSOs + return !(is_main_found && is_rtld_found && is_sdk_found); + }; + + // Search the directory recursively, looking for the required modules + const std::string directory = filepath.substr(0, filepath.find_last_of("/\\")) + DIR_SEP; + FileUtil::ForeachDirectoryEntry(nullptr, directory, callback); + + if (is_main_found && is_rtld_found && is_sdk_found) { + return FileType::DeconstructedRomDirectory; + } + + return FileType::Error; +} + +ResultStatus AppLoader_DeconstructedRomDirectory::Load( + Kernel::SharedPtr& process) { + if (is_loaded) { + return ResultStatus::ErrorAlreadyLoaded; + } + if (!file.IsOpen()) { + return ResultStatus::Error; + } + + process = Kernel::Process::Create("main"); + + // Load NSO modules + VAddr next_load_addr{Memory::PROCESS_IMAGE_VADDR}; + for (const auto& module : {"rtld", "main", "subsdk0", "subsdk1", "subsdk2", "subsdk3", + "subsdk4", "subsdk5", "subsdk6", "subsdk7", "sdk"}) { + const std::string path = + filepath.substr(0, filepath.find_last_of("/\\")) + DIR_SEP + module; + const VAddr load_addr = next_load_addr; + next_load_addr = AppLoader_NSO::LoadModule(path, load_addr); + if (next_load_addr) { + LOG_DEBUG(Loader, "loaded module %s @ 0x%llx", module, load_addr); + } else { + next_load_addr = load_addr; + } + } + + process->svc_access_mask.set(); + process->address_mappings = default_address_mappings; + process->resource_limit = + Kernel::ResourceLimit::GetForCategory(Kernel::ResourceLimitCategory::APPLICATION); + process->Run(Memory::PROCESS_IMAGE_VADDR, 48, Kernel::DEFAULT_STACK_SIZE); + + is_loaded = true; + return ResultStatus::Success; +} + +} // namespace Loader -- cgit v1.2.3 From 9b7e8a2e2b002f23ea4e4138d5f477d1cacc2b62 Mon Sep 17 00:00:00 2001 From: bunnei Date: Sat, 20 Jan 2018 15:48:37 -0500 Subject: loader: Clean up ctors and includes. --- src/core/loader/deconstructed_rom_directory.cpp | 5 +++++ src/core/loader/deconstructed_rom_directory.h | 4 +--- src/core/loader/elf.cpp | 3 +++ src/core/loader/elf.h | 3 +-- src/core/loader/loader.cpp | 4 +--- src/core/loader/loader.h | 5 +---- src/core/loader/nro.cpp | 4 ++++ src/core/loader/nro.h | 4 +--- src/core/loader/nso.cpp | 4 ++++ src/core/loader/nso.h | 4 +--- 10 files changed, 22 insertions(+), 18 deletions(-) (limited to 'src/core/loader/deconstructed_rom_directory.cpp') diff --git a/src/core/loader/deconstructed_rom_directory.cpp b/src/core/loader/deconstructed_rom_directory.cpp index daedeaab09..086ec11c8e 100644 --- a/src/core/loader/deconstructed_rom_directory.cpp +++ b/src/core/loader/deconstructed_rom_directory.cpp @@ -4,6 +4,7 @@ #include "common/common_funcs.h" #include "common/common_paths.h" +#include "common/file_util.h" #include "common/logging/log.h" #include "common/string_util.h" #include "core/hle/kernel/process.h" @@ -14,6 +15,10 @@ namespace Loader { +AppLoader_DeconstructedRomDirectory::AppLoader_DeconstructedRomDirectory(FileUtil::IOFile&& file, + std::string filepath) + : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + FileType AppLoader_DeconstructedRomDirectory::IdentifyType(FileUtil::IOFile& file, const std::string& filepath) { bool is_main_found{}; diff --git a/src/core/loader/deconstructed_rom_directory.h b/src/core/loader/deconstructed_rom_directory.h index d0391aac56..162541d547 100644 --- a/src/core/loader/deconstructed_rom_directory.h +++ b/src/core/loader/deconstructed_rom_directory.h @@ -6,7 +6,6 @@ #include #include "common/common_types.h" -#include "common/file_util.h" #include "core/hle/kernel/kernel.h" #include "core/loader/loader.h" @@ -20,8 +19,7 @@ namespace Loader { */ class AppLoader_DeconstructedRomDirectory final : public AppLoader { public: - AppLoader_DeconstructedRomDirectory(FileUtil::IOFile&& file, std::string filepath) - : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + AppLoader_DeconstructedRomDirectory(FileUtil::IOFile&& file, std::string filepath); /** * Returns the type of the file diff --git a/src/core/loader/elf.cpp b/src/core/loader/elf.cpp index a41d0b94a4..2f87346d04 100644 --- a/src/core/loader/elf.cpp +++ b/src/core/loader/elf.cpp @@ -364,6 +364,9 @@ SectionID ElfReader::GetSectionByName(const char* name, int firstSection) const namespace Loader { +AppLoader_ELF::AppLoader_ELF(FileUtil::IOFile&& file, std::string filename) + : AppLoader(std::move(file)), filename(std::move(filename)) {} + FileType AppLoader_ELF::IdentifyType(FileUtil::IOFile& file, const std::string&) { static constexpr u16 ELF_MACHINE_ARM{0x28}; diff --git a/src/core/loader/elf.h b/src/core/loader/elf.h index a5158338f7..ee741a7893 100644 --- a/src/core/loader/elf.h +++ b/src/core/loader/elf.h @@ -16,8 +16,7 @@ namespace Loader { /// Loads an ELF/AXF file class AppLoader_ELF final : public AppLoader { public: - AppLoader_ELF(FileUtil::IOFile&& file, std::string filename) - : AppLoader(std::move(file)), filename(std::move(filename)) {} + AppLoader_ELF(FileUtil::IOFile&& file, std::string filename); /** * Returns the type of the file diff --git a/src/core/loader/loader.cpp b/src/core/loader/loader.cpp index 9d87b07d7d..2ec08506dd 100644 --- a/src/core/loader/loader.cpp +++ b/src/core/loader/loader.cpp @@ -1,4 +1,4 @@ -// Copyright 2014 Citra Emulator Project +// Copyright 2018 yuzu emulator team // Licensed under GPLv2 or any later version // Refer to the license.txt file included. @@ -12,8 +12,6 @@ #include "core/loader/nro.h" #include "core/loader/nso.h" -//////////////////////////////////////////////////////////////////////////////////////////////////// - namespace Loader { const std::initializer_list default_address_mappings = { diff --git a/src/core/loader/loader.h b/src/core/loader/loader.h index 6075853b4a..dd44ee9a6d 100644 --- a/src/core/loader/loader.h +++ b/src/core/loader/loader.h @@ -1,4 +1,4 @@ -// Copyright 2014 Citra Emulator Project +// Copyright 2018 yuzu emulator team // Licensed under GPLv2 or any later version // Refer to the license.txt file included. @@ -20,9 +20,6 @@ struct AddressMapping; class Process; } // namespace Kernel -//////////////////////////////////////////////////////////////////////////////////////////////////// -// Loader namespace - namespace Loader { /// File types supported by CTR diff --git a/src/core/loader/nro.cpp b/src/core/loader/nro.cpp index ac730f8a31..0a087153f1 100644 --- a/src/core/loader/nro.cpp +++ b/src/core/loader/nro.cpp @@ -5,6 +5,7 @@ #include #include "common/common_funcs.h" +#include "common/file_util.h" #include "common/logging/log.h" #include "common/swap.h" #include "core/hle/kernel/process.h" @@ -45,6 +46,9 @@ struct ModHeader { }; static_assert(sizeof(ModHeader) == 0x1c, "ModHeader has incorrect size."); +AppLoader_NRO::AppLoader_NRO(FileUtil::IOFile&& file, std::string filepath) + : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + FileType AppLoader_NRO::IdentifyType(FileUtil::IOFile& file, const std::string&) { // Read NSO header NroHeader nro_header{}; diff --git a/src/core/loader/nro.h b/src/core/loader/nro.h index ae4c84fb7c..599adb2537 100644 --- a/src/core/loader/nro.h +++ b/src/core/loader/nro.h @@ -6,7 +6,6 @@ #include #include "common/common_types.h" -#include "common/file_util.h" #include "core/hle/kernel/kernel.h" #include "core/loader/linker.h" #include "core/loader/loader.h" @@ -16,8 +15,7 @@ namespace Loader { /// Loads an NRO file class AppLoader_NRO final : public AppLoader, Linker { public: - AppLoader_NRO(FileUtil::IOFile&& file, std::string filepath) - : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + AppLoader_NRO(FileUtil::IOFile&& file, std::string filepath); /** * Returns the type of the file diff --git a/src/core/loader/nso.cpp b/src/core/loader/nso.cpp index c80f2a1004..3ccbbb824c 100644 --- a/src/core/loader/nso.cpp +++ b/src/core/loader/nso.cpp @@ -5,6 +5,7 @@ #include #include #include "common/common_funcs.h" +#include "common/file_util.h" #include "common/logging/log.h" #include "common/swap.h" #include "core/hle/kernel/process.h" @@ -46,6 +47,9 @@ struct ModHeader { }; static_assert(sizeof(ModHeader) == 0x1c, "ModHeader has incorrect size."); +AppLoader_NSO::AppLoader_NSO(FileUtil::IOFile&& file, std::string filepath) + : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + FileType AppLoader_NSO::IdentifyType(FileUtil::IOFile& file, const std::string&) { u32 magic = 0; file.Seek(0, SEEK_SET); diff --git a/src/core/loader/nso.h b/src/core/loader/nso.h index f6a2b214f2..1ae30a824d 100644 --- a/src/core/loader/nso.h +++ b/src/core/loader/nso.h @@ -6,7 +6,6 @@ #include #include "common/common_types.h" -#include "common/file_util.h" #include "core/hle/kernel/kernel.h" #include "core/loader/linker.h" #include "core/loader/loader.h" @@ -16,8 +15,7 @@ namespace Loader { /// Loads an NSO file class AppLoader_NSO final : public AppLoader, Linker { public: - AppLoader_NSO(FileUtil::IOFile&& file, std::string filepath) - : AppLoader(std::move(file)), filepath(std::move(filepath)) {} + AppLoader_NSO(FileUtil::IOFile&& file, std::string filepath); /** * Returns the type of the file -- cgit v1.2.3