I’ve yet again been faced with the challenge of a slight hack in my code to accommodate for an unmodifiable library of some poorly written code.
After hours of research (after finding out you cannot pass any sort of state to a function pointer), I need to NOP out the ASM bytes within the function header that reset EAX to 0xCCCCCCCC.
By using the built in VC++ debugger to obtain the ‘address’ of the function and manually creating an array of bytes entry in cheat engine (which is surprisingly useful for this sort of thing), it successfully pulled up the bytes and I could NOP the 5 byte sequence manually.
However, doing this programmatically is a little different.
When I do any of the following, the address is significantly higher than what the debugger is reporting, this giving me a pointer to the wrong bytes.
unsigned int ptr = reinterpret_cast<unsigned int>(testhack);
unsigned char* tstc = (unsigned char*)&testhack;
FARPROC prc = GetProcAddress(GetModuleHandle("mod.dll"), "testhack"); // Still
// returns the incorrect address (same as the previous two)
What is the debugger doing to find the correct address? How can I find the correct address programmatically?
Figured it out.
Totally forgot about (what I believe are called) lookup tables. The address I was receiving was the pointer to the lookup table entry, which was a simple 5-byte unconditional JMP to the real function body. All I had to do was get the offset, add it to the end of the lookup table entry, and then I had my correct address.
Here is the code to reach the correct start address of the function.
tstthen holds the correct address!As of now, the calling ASM instructions put the pointer to the struct containing the function pointers into EAX. Normally, the callback function would reset EAX. However, I’ve applied this hack and NOP’d out that part. The first lines of code within the function create a local pointer, and then inline assembly to
mov [ptr],eaxthe address into the pointer. I can then use the pointer normally.