Перейти к содержанию

[C++ | DLL] Запись в выделенную память.


Рекомендуемые сообщения

Получаю нужные мне адреса.

DWORD from_addr = (DWORD)GetModuleHandle(L"Game.dll") + 0x36143B;
DWORD jmp_original = (DWORD)GetModuleHandle(L"Game.dll") + 0x361440;

В массив jmp записываю адрес прыжка обратно jmp_original, в оригинальный код.

BYTE jmp[5] = { 0xE9 };
memcpy(jmp + 1, (const void*)jmp_original, 4);

Далее выделяю память в размере 10 байт. 5 байт для нужной мне инструкции + 5 дня прыжка обратно.

DWORD alloc_addr = (DWORD)malloc(10); // выделяю память.
memcpy((void*)alloc_addr, (void*)from_addr, 5); // в первые 5 байт выделенной памяти записываю инструкцию размером 5 байт из оригинала.
memcpy((void*)(alloc_addr + 0x5), (void*)&jmp, 5); // в оставшиеся 5 байт, записываю адресс прыжка обратно.

 

После инъекции DLL в процесс, нахожу выделенную память, в итоге нужная инструкция скопировалась нормально, а вот прыжок обратно указывает совсем на другой адрес. СКРИНШОТ ИЗ CE выделенной памяти

Изменено пользователем Xhayla
Ссылка на комментарий
Поделиться на другие сайты


Так правильно.

const DWORD game_dll = (DWORD)GetModuleHandle(L"Game.dll");
const DWORD from_addr = game_dll + 0x36143B;
const DWORD jmp_original = game_dll + 0x361440;

 

void JMP(PBYTE buffer, DWORD A, DWORD B)
{
    buffer[0] = 0xE9;
    *(long*)&buffer[1] = long(B - A) - 5;
}

BYTE jmp[5];
JMP(jmp, alloc_addr + 0x5, jmp_original);
memcpy((void*)(alloc_addr + 0x5), (void*)jmp, 5);

Или так, если есть прямой доступ записи.

void JMP(DWORD A, DWORD B)
{
    PBYTE buffer = (PBYTE)A;
    buffer[0] = 0xE9;
    *(long*)&buffer[1] = long(B - A) - 5;
}

JMP(alloc_addr + 0x5, jmp_original);

 

Изменено пользователем Hack
Ссылка на комментарий
Поделиться на другие сайты

Спасибо, если не сложно, скажите пожалуйста, я изменяю Protect памяти на нужный мне, но, я указываю 5 байт, а он изменят защиту на всей странице, можно ли сделать так, чтобы он изменял защиту только 5 байт, которые я указал.

Если нет, то как программно узнать с какого адреса он изменил защиту?

VirtualProtect(reinterpret_cast<void*>(from_addr), 5, PAGE_EXECUTE_READWRITE | PAGE_GUARD, &dwOld);

 

Изменено пользователем Xhayla
Ссылка на комментарий
Поделиться на другие сайты

Нет, так как минимальное разделение страницы это 4096 байт.

DWORD getBaseAddress(DWORD Address)
{
    MEMORY_BASIC_INFORMATION mbi;
    if (!VirtualQuery((void*)Address, &mbi, sizeof(mbi)))
        return 0;
    return (DWORD)mbi.BaseAddress;
}

 

Ссылка на комментарий
Поделиться на другие сайты

×
×
  • Создать...

Важная информация

Находясь на нашем сайте, Вы автоматически соглашаетесь соблюдать наши Условия использования.