C ++ Function Hook (только адрес памяти)

У меня есть адрес памяти, это адрес памяти функции в другой программе (один из ее DLL). Я уже загружен в программу через инъекцию DLL. У меня уже есть адрес баса и фактическое расположение функции при каждой загрузке программы. Так что это не проблема.

Я хочу просто подключить это место и взять переменные. Я знаю псевдокод функции. Так что это не проблема. ИЛИ другой подход, который был бы хорош, — это создать точку останова в этой области памяти и получить регистры отладки.

Я не могу найти каких-либо четких примеров этого. У меня тоже нет «имени» функции, у меня просто есть адрес памяти. Есть ли способ работать только с адресом памяти? В большинстве, если не во всех примерах, вы используете имя функции, которого у меня нет.

Если бы кто-нибудь мог указать мне правильное направление, чтобы я мог выполнить эту задачу, я был бы очень признателен. Это также может помочь многим другим людям, у которых может возникнуть тот же вопрос.

редактироватьЯ должен также упомянуть, что я бы не стал перегружать мою программу чужим кодом, я просто хотел бы использовать barebone-файлы, очень похожие на обычную машину со свернутыми окнами. Никаких роскошных пакетов для меня, пожалуйста.

5

Решение

Вы пропустили самую важную часть, это для 32 или 64-битного кода? В любом случае, код проекта имеет хороший прирост и lib Вот это охватывает оба.

Если вы хотите сделать эту «старую школу», то это можно сделать довольно просто:

во-первых, вам нужно найти виртуальный адрес функции, которую вы хотите подключить (из-за ASLR вы никогда не должны полагаться на то, что она находится в том же месте), это обычно делается с помощью адреса базовой загрузки модуля RVA + для функции, которая не является экспортируется, для экспортируемых функций, вы можете использовать GetProcAddress,

Оттуда тип ловушки зависит от того, что вы хотите выполнить, в вашем случае есть два метода:

  1. исправить прыгать / вызывать вашу функцию в прологе целевой функции
  2. подключить все сайты вызовов к функции, которую вы хотите подключить, перенаправив на вашу функцию

первое проще, но грязно, так как обычно включает в себя некоторую встроенную сборку (если вы не подключаете /HOTPATCH бинарный или вы просто хотите его заглушить), второй намного чище, но требует немного работы с отладчиком.

Функция, к которой вы будете переходить, должна иметь те же параметры и соглашение о вызовах (ABI), что и функция, которую вы перехватываете. Эта функция позволяет вам захватывать переданные параметры, манипулировать ими, фильтровать вызовы или выполнять любые другие действия.

для обоих вам нужен способ написать какую-то сборку, чтобы сделать исправления, под windows, WriteProcessMemory ваш первый порт захода (примечание: для этого вам требуются разрешения RWX, следовательно, звонки на VirtualProtect), это небольшая служебная функция, которая создает 32-битный относительный вызов или переход (в зависимости от кода операции, переданного как eType)

#pragma pack(1)
struct patch_t
{
BYTE nPatchType;
DWORD dwAddress;
};
#pragma pack()

BOOL ApplyPatch(BYTE eType, DWORD dwAddress, const void* pTarget)
{
DWORD dwOldValue, dwTemp;
patch_t pWrite =
{
eType,
(DWORD)pTarget - (dwAddress + sizeof(DWORD) + sizeof(BYTE))
};

VirtualProtect((LPVOID)dwAddress,sizeof(DWORD),PAGE_EXECUTE_READWRITE,&dwOldValue);
BOOL bSuccess = WriteProcessMemory(GetCurrentProcess(),(LPVOID)dwAddress,&pWrite,sizeof(pWrite),NULL);
VirtualProtect((LPVOID)dwAddress,sizeof(DWORD),dwOldValue,&dwTemp);
return bSuccess;
}

Эта функция отлично работает для метода 2, но для метода 1 вам нужно перейти к промежуточному батуту сборки, чтобы восстановить любой код, который патч перезаписал перед возвратом к исходной функции, это становится очень утомительным, поэтому его лучше просто используйте существующую и протестированную библиотеку.

Судя по его звукам, использование метода 1 и исправление прыжка через пролог целевой функции сделают то, что вам нужно, так как кажется, что вам не нужно выполнять функцию, которую вы пропатчили.

(существует третий метод, использующий точки останова HW, но он очень хрупкий и может стать проблематичным, поскольку вы ограничены 4 точками останова HW).

4

Другие решения

Ваш «образец» здесь:

http://www.codeproject.com/Articles/4610/Three-Ways-to-Inject-Your-Code-into-Another-Proces#section_1

Обычно, когда вы «подключаетесь» к DLL, вы фактически помещаете свою функцию перед функцией в вызываемой DLL, поэтому вместо нее вызывается ваша функция. Затем вы захватываете все, что хотите, вызываете другую функцию, захватываете ее возвращаемые значения и все остальное, а затем возвращаетесь к исходному вызывающему.

0

По вопросам рекламы [email protected]