Stunts - the Game > Stunts Reverse Engineering

bypassing load.exe

(1/13) > >>

clvn:
hi!

using info on this forum, stunpack and bit of hacking, heres source code to a quick&dirty program that combines mcga.hdr, the uncompressed ega.cmn, mcga.cod and mcga.dif into a new game.exe. this new exe replaces load.exe/*.hdr/*.cmn/*.cod/*.dif.

made with msvc. some tweaks may be needed. enjoy!


--- Code: ---#include <fstream>

void next_offset(unsigned short* arg0, unsigned short* arg2, unsigned long arg4) {
unsigned short var2;
arg4 += *arg0;
var2 = arg4 / 0x10;
*arg2 += var2;
*arg0 = arg4 - (var2 << 4);
}

bool apply_dif(const char* filename, char* bytes) {
std::ifstream fs;
fs.open(filename, std::ios::in | std::ios::binary);

if (!fs) return false;

unsigned short var8;
unsigned char val1;
unsigned short output_ofs = 0x0000;
unsigned short output_seg = 0x0000;//0x01A7;

if (output_ofs == 0)
output_seg -= 0x1000;

output_ofs--;

next_offset(&output_ofs, &output_seg, 0);

while (true) {
fs.read((char*)&var8, sizeof(unsigned short));
if (var8 == 0) break; // eof

next_offset(&output_ofs, &output_seg, var8 & 0x7fff);

int pos = output_seg << 4 | output_ofs;
char* buffer = &bytes[pos];

fs.read((char*)buffer, sizeof(unsigned char));
fs.read((char*)&buffer[1], sizeof(unsigned char));

if ((var8 & 0x8000) != 0) {
fs.read((char*)&buffer[2], sizeof(unsigned char));
fs.read((char*)&buffer[3], sizeof(unsigned char));
}
}


fs.close();

return true;
}

size_t copy_binary(const char* filename, char* exeimage) {
std::ifstream fs;
fs.open(filename, std::ios::in | std::ios::binary);
if (!fs) return 0;
fs.seekg(0, SEEK_END);
size_t size = fs.tellg();
fs.seekg(0, SEEK_SET);

fs.read(exeimage, size);
fs.close();

return size;
}

void save_binary(std::string filename, char* image, int size) {
std::ofstream fs;
fs.open(filename.c_str(), std::ios::out | std::ios::binary);
fs.write(image, size);
fs.close();
}

int main() {

char exehdr[30];

copy_binary("assets\\mcga.hdr", exehdr);

unsigned short bytes_in_last_page = *(unsigned short*)((char*)&exehdr[2]);
unsigned short pages_in_executable = *(unsigned short*)((char*)&exehdr[4]);
unsigned short relocation_offset = *(unsigned short*)((char*)&exehdr[24]);
unsigned short paragraphs_in_header = *(unsigned short*)((char*)&exehdr[8]);

int executable_size = (pages_in_executable * 512);
if (bytes_in_last_page > 0)
executable_size += -512 + bytes_in_last_page;

int header_size = paragraphs_in_header * 16;

char* exeimage = new char[executable_size];
memcpy(exeimage, exehdr, 30);

int size = copy_binary("assets\\ega.cmn", &exeimage[header_size]);
apply_dif("assets\\mcga.dif", &exeimage[header_size]);
copy_binary("assets\\mcga.cod", &exeimage[header_size + size]);

save_binary("game.exe", exeimage, executable_size);
return 0;
}

--- End code ---

clvn:
some further analysis reveals the the output game.exe from the above program is compressed with exepack, as with load.exe.

to remove the copy protection, uncompress with unp and put a byte 0x1 at offset 0x2b3c :-)

clvn:
hello again!

ive put game.exe through idapro and worked through random portions of the disassembly. so far its been adhoc hacking, trying to figure out the general structure and flow of the game.

if anyones interested, heres the output game.asm so far: http://dl.getdropbox.com/u/213479/game.asm . also id be happy to share the .idb as well.

of the 500+ functions detected in the exe, about half of them are named roughly after their category or function. the others still have cryptic names like "sub_9F1_2564". the main()-function is right at the beginning of the file (after the struct declarations).


dunno if it is documented somewhere else, but according to the command line parsing code, the exe understands the following parameters:

/ns - no sound
/nb - parsed, but unused
/ssb - use soundblaster (ad15.drv) instead of pc speaker
/sXY - use driver XY15.drv instead of pc speaker (e.g /sad for soundblaster)
/h - sets bios video mode 4 (black screen here)

BonzaiJoe:
Hi clvn! And welcome.

Forgive my ignorance, but what is the point of bypassing load.exe? What can be achieved with this utility?

Duplode:

--- Quote from: BonzaiJoe on October 26, 2009, 10:52:48 PM ---Forgive my ignorance, but what is the point of bypassing load.exe? What can be achieved with this utility?

--- End quote ---

If I understood correctly what Cas mentioned somewhere long ago, load.exe picks a number of code files (according for different video/sound rivers, etc.) and combines them into a single piece of code which is run as the game. Getting it off the way should make it easier to locate which parts of the executable(s) are responsible for which functions within the game - that is, doing reverse engineering on whatever is buried inside the code.

As for me, I have no disassembly knowledge to be able to help, but highly appreciate the efforts anyway  :) Too bad Cas and the other hackers haven't been around lately...

Navigation

[0] Message Index

[#] Next page

Go to full version