diff options
| author | aerosoul <aerosoul94@hotmail.com> | 2019-10-28 13:59:30 -0500 |
|---|---|---|
| committer | Rick Gibbed <rick@gibbed.us> | 2019-11-20 18:09:28 -0600 |
| commit | bc8b62909291017f4867ceaa1b46f1654a0aaefa (patch) | |
| tree | 0f05a66664e16983dcfa45e11376241bb4ebc4a7 | |
| parent | 03d5455a2f8b5c5d029d7612a37cf7a24a64fc18 (diff) | |
[Kernel] Enable XEX1 loading
| -rw-r--r-- | src/xenia/cpu/xex_module.cc | 41 | ||||
| -rw-r--r-- | src/xenia/cpu/xex_module.h | 24 | ||||
| -rw-r--r-- | src/xenia/kernel/user_module.cc | 2 | ||||
| -rw-r--r-- | src/xenia/kernel/util/xex2_info.h | 17 |
4 files changed, 75 insertions, 9 deletions
diff --git a/src/xenia/cpu/xex_module.cc b/src/xenia/cpu/xex_module.cc index e842b58b4..09cea5143 100644 --- a/src/xenia/cpu/xex_module.cc +++ b/src/xenia/cpu/xex_module.cc @@ -103,10 +103,9 @@ bool XexModule::GetOptHeader(xex2_header_keys key, void** out_ptr) const { return XexModule::GetOptHeader(xex_header(), key, out_ptr); } -const xex2_security_info* XexModule::GetSecurityInfo( - const xex2_header* header) { - return reinterpret_cast<const xex2_security_info*>(uintptr_t(header) + - header->security_offset); +const void* XexModule::GetSecurityInfo(const xex2_header* header) { + return reinterpret_cast<const void*>(uintptr_t(header) + + header->security_offset); } const PESection* XexModule::GetPESection(const char* name) { @@ -870,7 +869,11 @@ bool XexModule::Load(const std::string& name, const std::string& path, const void* xex_addr, size_t xex_length) { auto src_header = reinterpret_cast<const xex2_header*>(xex_addr); - if (src_header->magic != 'XEX2') { + if (src_header->magic == 'XEX1') { + xex_format_ = kFormatXex1; + } else if (src_header->magic == 'XEX2') { + xex_format_ = kFormatXex2; + } else { return false; } @@ -881,6 +884,34 @@ bool XexModule::Load(const std::string& name, const std::string& path, xex_header_mem_.resize(src_header->header_size); std::memcpy(xex_header_mem_.data(), src_header, src_header->header_size); + if (xex_format_ == kFormatXex1) { + const xex1_security_info* xex1_sec_info = + reinterpret_cast<const xex1_security_info*>( + GetSecurityInfo(xex_header())); + + security_info_.rsa_signature = xex1_sec_info->rsa_signature; + security_info_.aes_key = xex1_sec_info->aes_key; + security_info_.image_size = xex1_sec_info->image_size; + security_info_.image_flags = xex1_sec_info->image_flags; + security_info_.export_table = xex1_sec_info->export_table; + security_info_.load_address = xex1_sec_info->load_address; + security_info_.page_descriptor_count = xex1_sec_info->page_descriptor_count; + security_info_.page_descriptors = xex1_sec_info->page_descriptors; + } else if (xex_format_ == kFormatXex2) { + const xex2_security_info* xex2_sec_info = + reinterpret_cast<const xex2_security_info*>( + GetSecurityInfo(xex_header())); + + security_info_.rsa_signature = xex2_sec_info->rsa_signature; + security_info_.aes_key = xex2_sec_info->aes_key; + security_info_.image_size = xex2_sec_info->image_size; + security_info_.image_flags = xex2_sec_info->image_flags; + security_info_.export_table = xex2_sec_info->export_table; + security_info_.load_address = xex2_sec_info->load_address; + security_info_.page_descriptor_count = xex2_sec_info->page_descriptor_count; + security_info_.page_descriptors = xex2_sec_info->page_descriptors; + } + auto sec_header = xex_security_info(); // Try setting our base_address based on XEX_HEADER_IMAGE_BASE_ADDRESS, fall diff --git a/src/xenia/cpu/xex_module.h b/src/xenia/cpu/xex_module.h index 5c8cb8d6b..e2c5f5a3b 100644 --- a/src/xenia/cpu/xex_module.h +++ b/src/xenia/cpu/xex_module.h @@ -43,6 +43,21 @@ class XexModule : public xe::cpu::Module { xe_xex2_version_t min_version; std::vector<ImportLibraryFn> imports; }; + struct SecurityInfoContext { + const char* rsa_signature; + const char* aes_key; + uint32_t image_size; + uint32_t image_flags; + uint32_t export_table; + uint32_t load_address; + uint32_t page_descriptor_count; + const xex2_page_descriptor* page_descriptors; + }; + enum XexFormat { + kFormatUnknown, + kFormatXex1, + kFormatXex2, + }; XexModule(Processor* processor, kernel::KernelState* kernel_state); virtual ~XexModule(); @@ -51,8 +66,8 @@ class XexModule : public xe::cpu::Module { const xex2_header* xex_header() const { return reinterpret_cast<const xex2_header*>(xex_header_mem_.data()); } - const xex2_security_info* xex_security_info() const { - return GetSecurityInfo(xex_header()); + const SecurityInfoContext* xex_security_info() const { + return &security_info_; } uint32_t image_size() const { @@ -112,7 +127,7 @@ class XexModule : public xe::cpu::Module { return GetOptHeader(key, reinterpret_cast<void**>(out_ptr)); } - static const xex2_security_info* GetSecurityInfo(const xex2_header* header); + static const void* GetSecurityInfo(const xex2_header* header); const PESection* GetPESection(const char* name); @@ -186,6 +201,9 @@ class XexModule : public xe::cpu::Module { uint32_t base_address_ = 0; uint32_t low_address_ = 0; uint32_t high_address_ = 0; + + XexFormat xex_format_ = kFormatUnknown; + SecurityInfoContext security_info_ = {}; }; } // namespace cpu diff --git a/src/xenia/kernel/user_module.cc b/src/xenia/kernel/user_module.cc index 2d070a65a..58ab9f36c 100644 --- a/src/xenia/kernel/user_module.cc +++ b/src/xenia/kernel/user_module.cc @@ -135,7 +135,7 @@ X_STATUS UserModule::LoadFromMemory(const void* addr, const size_t length) { auto processor = kernel_state()->processor(); auto magic = xe::load_and_swap<uint32_t>(addr); - if (magic == 'XEX2') { + if (magic == 'XEX2' || magic == 'XEX1') { module_format_ = kModuleFormatXex; } else if (magic == 0x7F454C46 /* 0x7F 'ELF' */) { module_format_ = kModuleFormatElf; diff --git a/src/xenia/kernel/util/xex2_info.h b/src/xenia/kernel/util/xex2_info.h index f91b7c30f..6203b18f2 100644 --- a/src/xenia/kernel/util/xex2_info.h +++ b/src/xenia/kernel/util/xex2_info.h @@ -544,6 +544,23 @@ struct xex2_security_info { xex2_page_descriptor page_descriptors[1]; // 0x184 }; +struct xex1_security_info { + xe::be<uint32_t> header_size; + xe::be<uint32_t> image_size; + char rsa_signature[0x100]; + char image_digest[0x14]; + char import_table_digest[0x14]; + xe::be<uint32_t> load_address; + char aes_key[0x10]; + char xgd2_media_id[0x10]; + xe::be<uint32_t> region; + xe::be<uint32_t> image_flags; + xe::be<uint32_t> export_table; + xe::be<uint32_t> allowed_media_types; + xe::be<uint32_t> page_descriptor_count; + xex2_page_descriptor page_descriptors[1]; +}; + struct xex2_export_table { xe::be<uint32_t> magic[3]; // 0x0 xe::be<uint32_t> modulenumber[2]; // 0xC |
