mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-02-24 18:39:56 +00:00
elf: handle decompress flag for 32 bit elfs
This commit is contained in:
parent
b3a933ba84
commit
095d02e41b
@ -1274,115 +1274,13 @@ fs::file SELFDecrypter::MakeElf(bool isElf32)
|
|||||||
// Create a new ELF file.
|
// Create a new ELF file.
|
||||||
fs::file e = fs::make_stream<std::vector<u8>>();
|
fs::file e = fs::make_stream<std::vector<u8>>();
|
||||||
|
|
||||||
// Set initial offset.
|
|
||||||
u32 data_buf_offset = 0;
|
|
||||||
|
|
||||||
if (isElf32)
|
if (isElf32)
|
||||||
{
|
{
|
||||||
// Write ELF header.
|
WriteElf(e, elf32_hdr, shdr32_arr, phdr32_arr);
|
||||||
WriteEhdr(e, elf32_hdr);
|
|
||||||
|
|
||||||
// Write program headers.
|
|
||||||
for (u32 i = 0; i < elf32_hdr.e_phnum; ++i)
|
|
||||||
{
|
|
||||||
WritePhdr(e, phdr32_arr[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (unsigned int i = 0; i < meta_hdr.section_count; i++)
|
|
||||||
{
|
|
||||||
// PHDR type.
|
|
||||||
if (meta_shdr[i].type == 2)
|
|
||||||
{
|
|
||||||
// Seek to the program header data offset and write the data.
|
|
||||||
e.seek(phdr32_arr[meta_shdr[i].program_idx].p_offset);
|
|
||||||
e.write(data_buf.get() + data_buf_offset, meta_shdr[i].data_size);
|
|
||||||
|
|
||||||
// Advance the data buffer offset by data size.
|
|
||||||
data_buf_offset += meta_shdr[i].data_size;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write section headers.
|
|
||||||
if (self_hdr.se_shdroff != 0)
|
|
||||||
{
|
|
||||||
e.seek(elf32_hdr.e_shoff);
|
|
||||||
|
|
||||||
for (u32 i = 0; i < elf32_hdr.e_shnum; ++i)
|
|
||||||
{
|
|
||||||
WriteShdr(e, shdr32_arr[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Write ELF header.
|
WriteElf(e, elf64_hdr, shdr64_arr, phdr64_arr);
|
||||||
WriteEhdr(e, elf64_hdr);
|
|
||||||
|
|
||||||
// Write program headers.
|
|
||||||
for (u32 i = 0; i < elf64_hdr.e_phnum; ++i)
|
|
||||||
{
|
|
||||||
WritePhdr(e, phdr64_arr[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write data.
|
|
||||||
for (unsigned int i = 0; i < meta_hdr.section_count; i++)
|
|
||||||
{
|
|
||||||
// PHDR type.
|
|
||||||
if (meta_shdr[i].type == 2)
|
|
||||||
{
|
|
||||||
// Decompress if necessary.
|
|
||||||
if (meta_shdr[i].compressed == 2)
|
|
||||||
{
|
|
||||||
// Store the length in writeable memory space.
|
|
||||||
std::unique_ptr<uLongf> decomp_buf_length(new uLongf);
|
|
||||||
memcpy(decomp_buf_length.get(), &phdr64_arr[meta_shdr[i].program_idx].p_filesz, sizeof(uLongf));
|
|
||||||
|
|
||||||
/// Create a pointer to a buffer for decompression.
|
|
||||||
std::unique_ptr<u8[]> decomp_buf(new u8[phdr64_arr[meta_shdr[i].program_idx].p_filesz]);
|
|
||||||
|
|
||||||
// Create a buffer separate from data_buf to uncompress.
|
|
||||||
std::unique_ptr<u8[]> zlib_buf(new u8[data_buf_length]);
|
|
||||||
memcpy(zlib_buf.get(), data_buf.get(), data_buf_length);
|
|
||||||
|
|
||||||
// Use zlib uncompress on the new buffer.
|
|
||||||
// decomp_buf_length changes inside the call to uncompress, so it must be a pointer to correct type (in writeable mem space).
|
|
||||||
int rv = uncompress(decomp_buf.get(), decomp_buf_length.get(), zlib_buf.get() + data_buf_offset, data_buf_length);
|
|
||||||
|
|
||||||
// Check for errors (TODO: Probably safe to remove this once these changes have passed testing.)
|
|
||||||
switch (rv)
|
|
||||||
{
|
|
||||||
case Z_MEM_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_MEM_ERROR!"); break;
|
|
||||||
case Z_BUF_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_BUF_ERROR!"); break;
|
|
||||||
case Z_DATA_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_DATA_ERROR!"); break;
|
|
||||||
default: break;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Seek to the program header data offset and write the data.
|
|
||||||
e.seek(phdr64_arr[meta_shdr[i].program_idx].p_offset);
|
|
||||||
e.write(decomp_buf.get(), phdr64_arr[meta_shdr[i].program_idx].p_filesz);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// Seek to the program header data offset and write the data.
|
|
||||||
e.seek(phdr64_arr[meta_shdr[i].program_idx].p_offset);
|
|
||||||
e.write(data_buf.get() + data_buf_offset, meta_shdr[i].data_size);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Advance the data buffer offset by data size.
|
|
||||||
data_buf_offset += meta_shdr[i].data_size;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write section headers.
|
|
||||||
if (self_hdr.se_shdroff != 0)
|
|
||||||
{
|
|
||||||
e.seek(elf64_hdr.e_shoff);
|
|
||||||
|
|
||||||
for (u32 i = 0; i < elf64_hdr.e_shnum; ++i)
|
|
||||||
{
|
|
||||||
WriteShdr(e, shdr64_arr[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return e;
|
return e;
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "key_vault.h"
|
#include "key_vault.h"
|
||||||
|
#include "zlib.h"
|
||||||
|
|
||||||
struct AppInfo
|
struct AppInfo
|
||||||
{
|
{
|
||||||
@ -414,6 +415,82 @@ public:
|
|||||||
bool DecryptData();
|
bool DecryptData();
|
||||||
bool DecryptNPDRM(u8 *metadata, u32 metadata_size);
|
bool DecryptNPDRM(u8 *metadata, u32 metadata_size);
|
||||||
bool GetKeyFromRap(u8 *content_id, u8 *npdrm_key);
|
bool GetKeyFromRap(u8 *content_id, u8 *npdrm_key);
|
||||||
|
|
||||||
|
private:
|
||||||
|
template<typename EHdr, typename SHdr, typename PHdr>
|
||||||
|
void WriteElf(fs::file& e, EHdr ehdr, SHdr shdr, PHdr phdr)
|
||||||
|
{
|
||||||
|
// Set initial offset.
|
||||||
|
u32 data_buf_offset = 0;
|
||||||
|
|
||||||
|
// Write ELF header.
|
||||||
|
WriteEhdr(e, ehdr);
|
||||||
|
|
||||||
|
// Write program headers.
|
||||||
|
for (u32 i = 0; i < ehdr.e_phnum; ++i)
|
||||||
|
{
|
||||||
|
WritePhdr(e, phdr[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (unsigned int i = 0; i < meta_hdr.section_count; i++)
|
||||||
|
{
|
||||||
|
// PHDR type.
|
||||||
|
if (meta_shdr[i].type == 2)
|
||||||
|
{
|
||||||
|
// Decompress if necessary.
|
||||||
|
if (meta_shdr[i].compressed == 2)
|
||||||
|
{
|
||||||
|
const auto filesz = phdr[meta_shdr[i].program_idx].p_filesz;
|
||||||
|
|
||||||
|
// Create a pointer to a buffer for decompression.
|
||||||
|
std::unique_ptr<u8[]> decomp_buf(new u8[filesz]);
|
||||||
|
|
||||||
|
// Create a buffer separate from data_buf to uncompress.
|
||||||
|
std::unique_ptr<u8[]> zlib_buf(new u8[data_buf_length]);
|
||||||
|
memcpy(zlib_buf.get(), data_buf.get(), data_buf_length);
|
||||||
|
|
||||||
|
uLongf decomp_buf_length = ::narrow<uLongf>(filesz);
|
||||||
|
|
||||||
|
// Use zlib uncompress on the new buffer.
|
||||||
|
// decomp_buf_length changes inside the call to uncompress
|
||||||
|
int rv = uncompress(decomp_buf.get(), &decomp_buf_length, zlib_buf.get() + data_buf_offset, data_buf_length);
|
||||||
|
|
||||||
|
// Check for errors (TODO: Probably safe to remove this once these changes have passed testing.)
|
||||||
|
switch (rv)
|
||||||
|
{
|
||||||
|
case Z_MEM_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_MEM_ERROR!"); break;
|
||||||
|
case Z_BUF_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_BUF_ERROR!"); break;
|
||||||
|
case Z_DATA_ERROR: LOG_ERROR(LOADER, "MakeELF encountered a Z_DATA_ERROR!"); break;
|
||||||
|
default: break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Seek to the program header data offset and write the data.
|
||||||
|
e.seek(phdr[meta_shdr[i].program_idx].p_offset);
|
||||||
|
e.write(decomp_buf.get(), filesz);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Seek to the program header data offset and write the data.
|
||||||
|
e.seek(phdr[meta_shdr[i].program_idx].p_offset);
|
||||||
|
e.write(data_buf.get() + data_buf_offset, meta_shdr[i].data_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Advance the data buffer offset by data size.
|
||||||
|
data_buf_offset += meta_shdr[i].data_size;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write section headers.
|
||||||
|
if (self_hdr.se_shdroff != 0)
|
||||||
|
{
|
||||||
|
e.seek(ehdr.e_shoff);
|
||||||
|
|
||||||
|
for (u32 i = 0; i < ehdr.e_shnum; ++i)
|
||||||
|
{
|
||||||
|
WriteShdr(e, shdr[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
extern fs::file decrypt_self(fs::file elf_or_self, u8* klic_key = nullptr);
|
extern fs::file decrypt_self(fs::file elf_or_self, u8* klic_key = nullptr);
|
||||||
|
@ -107,20 +107,20 @@
|
|||||||
<IgnoreImportLibrary Condition="'$(Configuration)|$(Platform)'=='Debug - LLVM|x64'">true</IgnoreImportLibrary>
|
<IgnoreImportLibrary Condition="'$(Configuration)|$(Platform)'=='Debug - LLVM|x64'">true</IgnoreImportLibrary>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||||
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include</IncludePath>
|
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include;..\3rdparty\zlib</IncludePath>
|
||||||
<LibraryPath>$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
<LibraryPath>$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug - LLVM|x64'">
|
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug - LLVM|x64'">
|
||||||
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include</IncludePath>
|
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include;..\3rdparty\zlib</IncludePath>
|
||||||
<LibraryPath>$(SolutionDir)lib\Debug-x64;$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
<LibraryPath>$(SolutionDir)lib\Debug-x64;$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||||
<LibraryPath>$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
<LibraryPath>$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
||||||
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include</IncludePath>
|
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include;..\3rdparty\zlib</IncludePath>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release - LLVM|x64'">
|
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release - LLVM|x64'">
|
||||||
<LibraryPath>$(SolutionDir)lib\Release-x64;$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
<LibraryPath>$(SolutionDir)lib\Release-x64;$(SolutionDir)lib\$(Configuration)-$(Platform)\;$(UniversalCRT_LibraryPath_x64);$(LibraryPath)</LibraryPath>
|
||||||
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include</IncludePath>
|
<IncludePath>..\3rdparty\hidapi\hidapi;.\;..\;..\asmjit\src;..\3rdparty\yaml-cpp\include;..\3rdparty\ffmpeg\WindowsInclude;..\3rdparty\cereal\include;..\3rdparty\ffmpeg\Windows\x86_64\Include;$(VC_IncludePath);$(WindowsSDK_IncludePath);$(UniversalCRT_IncludePath);..\3rdparty\minidx12\Include;..\3rdparty\GSL\include;..\3rdparty\libpng;..\3rdparty\GL;..\3rdparty\stblib;..\3rdparty\OpenAL\include;..\3rdparty\pugixml\src;..\3rdparty\Optional;..\3rdparty\discord-rpc\include;..\3rdparty\zlib</IncludePath>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||||
<ClCompile>
|
<ClCompile>
|
||||||
|
Loading…
x
Reference in New Issue
Block a user