Внедрение DLL (Dynamic Link Library) в процессы — мощный инструмент, используемый для модификации поведения программ, отладки или расширения функциональности. Однако при работе с 64-битными приложениями в Delphi разработчики сталкиваются с рядом проблем, связанных с архитектурными отличиями x64 и ограничениями Windows API. В этой статье мы рассмотрим, как создать инжектор DLL для x64 приложений на Delphi, а также разберём типичные ошибки и способы их исправления.
1. Основные методы внедрения DLL
Существует несколько способов загрузить DLL в чужой процесс:
CreateRemoteThread + LoadLibrary
Самый распространённый метод, использующий API-функции Windows.
Использование SetWindowsHookEx
Подходит для внедрения в GUI-приложения.
Модификация импорта (IAT Hooking)
Изменение таблицы импорта целевого процесса.
Manual Mapping
Ручное отображение DLL в память процесса.
Мы сосредоточимся на первом методе, так как он наиболее универсален.
2. Пример кода x64 инжектора на Delphi
function InjectDLL(const ProcessID: Cardinal; const DLLPath: string): Boolean;
var
hProcess: THandle;
hThread: THandle;
pRemoteBuffer: Pointer;
pLoadLibrary: Pointer;
BytesWritten: NativeUInt;
ThreadID: Cardinal;
begin
Result := False;
// Открываем процесс с правами на запись и создание потоков
hProcess := OpenProcess(PROCESS_CREATE_THREAD or PROCESS_QUERY_INFORMATION or
PROCESS_VM_OPERATION or PROCESS_VM_WRITE or PROCESS_VM_READ,
False, ProcessID);
if hProcess = 0 then Exit;
try
// Выделяем память в целевом процессе под путь к DLL
pRemoteBuffer := VirtualAllocEx(hProcess, nil, Length(DLLPath) * SizeOf(Char) + 1,
MEM_COMMIT or MEM_RESERVE, PAGE_READWRITE);
if pRemoteBuffer = nil then Exit;
try
// Записываем путь к DLL в выделенную память
if not WriteProcessMemory(hProcess, pRemoteBuffer, PChar(DLLPath),
Length(DLLPath) * SizeOf(Char) + 1, BytesWritten) then Exit;
// Получаем адрес LoadLibraryW (для Unicode-версии)
pLoadLibrary := GetProcAddress(GetModuleHandle('kernel32.dll'), 'LoadLibraryW');
if pLoadLibrary = nil then Exit;
// Создаём удалённый поток, который вызовет LoadLibrary
hThread := CreateRemoteThread(hProcess, nil, 0, pLoadLibrary, pRemoteBuffer, 0, ThreadID);
if hThread = 0 then Exit;
try
WaitForSingleObject(hThread, INFINITE);
Result := True;
finally
CloseHandle(hThread);
end;
finally
VirtualFreeEx(hProcess, pRemoteBuffer, 0, MEM_RELEASE);
end;
finally
CloseHandle(hProcess);
end;
end;
3. Типичные проблемы и их решения
Проблема 1: Ошибки при работе с 64-битными процессами
Если целевое приложение x64, а инжектор x86 (или наоборот), внедрение не сработает.
Решение:
- Скомпилируйте инжектор в той же разрядности, что и целевой процесс.
- Используйте IsWow64Process для проверки разрядности процесса.
function IsProcess64Bit(const ProcessID: Cardinal): Boolean;
var
hProcess: THandle;
IsWow64: BOOL;
begin
hProcess := OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, False, ProcessID);
if hProcess = 0 then Exit(False);
try
Result := IsWow64Process(hProcess, IsWow64) and not IsWow64;
finally
CloseHandle(hProcess);
end;
end;
Проблема 2: Невозможность записи в память процесса
Некоторые процессы (например, защищённые антивирусами) блокируют VirtualAllocEx и WriteProcessMemory.
Решение:
- Используйте более сложные техники, например, Manual Mapping.
- Попробуйте внедрение через SetWindowsHookEx.
Проблема 3: DLL не загружается из-за неправильного пути
Если путь к DLL содержит кириллицу или пробелы, LoadLibrary может не сработать.
Решение:
- Убедитесь, что путь в Unicode (LoadLibraryW).
- Используйте абсолютные пути.
4. Альтернативные методы внедрения
Manual Mapping
Этот метод предполагает ручное отображение DLL в память процесса без использования LoadLibrary.
Преимущества:
- Обходит некоторые защиты.
- Позволяет скрыть факт загрузки DLL.
Недостатки:
- Сложнее в реализации.
- Требует обработки релокаций и импортов.
Заключение
Создание инжектора DLL для x64 процессов в Delphi требует учёта разрядности, корректной работы с памятью и обхода возможных защит. Предложенный метод на основе CreateRemoteThread и LoadLibrary — самый простой, но не всегда эффективный. В сложных случаях стоит рассмотреть альтернативные подходы, такие как Manual Mapping.
Если у вас есть вопросы или предложения по оптимизации кода, оставляйте их в комментариях!
Описание разработки x64 инжектора DLL на Delphi, включая методы внедрения, типичные проблемы и их решения.
Комментарии и вопросы
Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS
Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.