Здравствуйте!
Пишу приложения на С++ (на основе MFC).
В моем боте большинство инжектируемых функций имеют очень простой вид: заталкивают параметры в стек и вызывают функцию. Вот пример:
Код:
//Инжект прыжка
typedef int (__thiscall * fnJump)(LPVOID PlayerBase, DWORD Reserved);
VOID JumpInject(DWORD * ParamPointer)
{
((fnJump)0x00457540)(*(LPVOID *)(*(LPBYTE *)GAME_ADDRESS + 0x20), *ParamPointer);
}
BOOL CPlayerBot::Jump(DWORD Reserved)
{
return Inject(JumpInject, 2048, NULL, &Reserved, sizeof(Reserved));
}
С такими функциями не возникает никаких проблем.
Но когда пытаюсь сделать что-то посложнее, бот либо работает не правильно, либо вообще вылетает. По генерируемому коду я нашел несколько причин. Например, константы с плавающей точкой не используются как непосредственные операнды а хранятся отдельно в памяти. Обращение к ним происходит так:
00408086 DC 0D 98 EC 41 00 fmul qword ptr [__real@4040000000000000 (41EC98h)]
Естественно в памяти другого процесса по этому адресу прочитается мусор.
А вот пример причины вылета:
3258: int StartPointX = (ParamPointer->StartPoint.x - ParamPointer->GridOrigin.x) / ParamPointer->GridStep;
mov edx,dword ptr [ParamPointer]
fld dword ptr [edx]
mov eax,dword ptr [ParamPointer]
fsub dword ptr [eax+0Ch]
mov ecx,dword ptr [ParamPointer]
fdiv dword ptr [ecx+18h]
call _ftol2_sse (416A60h) <---------- ВЫЗОВ ПО АДРЕСУ, ГДЕ НАХОДИТСЯ МУСОР!!! ГАРАНТИРОВАННЫЙ ВЫЛЕТ!!!
mov dword ptr [StartPointX],eax
Запрет оптимизации и инкрементал линкинга не помогает. В принципе можно на ассемблере обойти проблемные области, но охота что бы все красиво было.
Как мне еще настроить параметры проекта в Visual Studio 2008 что бы избежать вышеперечисленных проблем с чтением и вызовом мусора?