@@ -34,19 +34,46 @@ namespace {
3434EXEReader::EXEReader (Filesystem_Stream::InputStream core) : corefile(std::move(core)) {
3535 // The Incredibly Dumb PE parser (tm)
3636 // Extracts data from the resource section for engine detection and can read ExFont.
37- uint32_t ofs = GetU32 (0x3C );
37+ uint32_t ofs = GetU32 (0x3C ); // PE header offset
3838 uint16_t machine = GetU16 (ofs + 4 );
39- if (machine != 0x14c ) {
40- // FIXME: Newer versions of Maniac Patch can be 64 Bit
41- Output::Debug (" EXEReader: Machine type is not i386 ({:#x})" , machine);
42- file_info.is_i386 = false ;
43- return ;
39+
40+ switch (machine) {
41+ case 0x14c :
42+ file_info.machine_type = MachineType::i386;
43+ break ;
44+ case 0x8664 :
45+ file_info.machine_type = MachineType::amd64;
46+ break ;
47+ default :
48+ Output::Debug (" EXEReader: Unsupported machine type ({:#x})" , machine);
49+ file_info.machine_type = MachineType::Unknown;
50+ return ;
4451 }
4552
4653 // The largest known exe has 11 segments, guard against bogus section data here
4754 uint16_t sections = std::min<uint16_t >(GetU16 (ofs + 6 ), 11 );
48- uint32_t sectionsOfs = ofs + 0x18 + GetU16 (ofs + 0x14 );
49- resource_rva = GetU32 (ofs + 0x88 );
55+ uint32_t optional_header = ofs + 0x18 ;
56+ uint32_t oh_magic = GetU16 (optional_header);
57+
58+ bool format_pe32;
59+
60+ switch (oh_magic) {
61+ case 0x10b :
62+ format_pe32 = true ;
63+ break ;
64+ case 0x20b :
65+ // PE32+ (for 64 bit executables)
66+ format_pe32 = false ;
67+ break ;
68+ default :
69+ Output::Debug (" EXEReader: Unknown PE header magic ({:#x})" , oh_magic);
70+ file_info.machine_type = MachineType::Unknown;
71+ return ;
72+ }
73+
74+ uint32_t sectionsOfs = optional_header + GetU16 (ofs + 0x14 ); // skip opt header
75+ uint32_t data_directory_ofs = (format_pe32 ? 0x60 : 0x70 );
76+ resource_rva = GetU32 (optional_header + data_directory_ofs + 16 );
5077 if (!resource_rva) {
5178 // Is some kind of encrypted EXE -> Give up
5279 return ;
@@ -379,13 +406,13 @@ bool EXEReader::ResNameCheck(uint32_t i, const char* p) {
379406}
380407
381408void EXEReader::FileInfo::Print () const {
382- Output::Debug (" RPG_RT information: version={} logos={} code={:#x} cherry={:#x} geep={:#x} i386 ={} easyrpg={}" , version_str, logos, code_size, cherry_size, geep_size, is_i386 , is_easyrpg_player);
409+ Output::Debug (" RPG_RT information: version={} logos={} code={:#x} cherry={:#x} geep={:#x} arch ={} easyrpg={}" , version_str, logos, code_size, cherry_size, geep_size, kMachineTypes [machine_type] , is_easyrpg_player);
383410}
384411
385412int EXEReader::FileInfo::GetEngineType (bool & is_maniac_patch) const {
386413 is_maniac_patch = false ;
387414
388- if (is_easyrpg_player || !is_i386 ) {
415+ if (is_easyrpg_player || machine_type == MachineType::Unknown ) {
389416 return Player::EngineNone;
390417 }
391418
0 commit comments