德尔福的问题转换EAT VirtualProtect的挂钩程序从C到德尔福 [英] Delphi problems converting VirtualProtect EAT hook routines from C to Delphi
问题描述
我想转换这些来自的 CHook 论坛发帖此code这确实EAT挂钩:
I'm trying to convert this code which came from CHook forum posting this code which does EAT hooking:
#include <Windows.h>
#include <Psapi.h>
#include <string>
#if PSAPI_VERSION == 1
#pragma comment(lib, "Psapi.lib")
#endif
template <typename DestType, typename SrcType>
DestType* ByteOffset(SrcType* ptr, ptrdiff_t offset)
{
return reinterpret_cast<DestType*>(reinterpret_cast<unsigned char*>(ptr) + offset);
}
bool eat_hook(void* old_function, void* new_function)
{
HMODULE hModule;
GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, (LPCSTR)old_function, &hModule);
PIMAGE_DOS_HEADER DosHeader = (PIMAGE_DOS_HEADER)hModule;
PIMAGE_NT_HEADERS NtHeader = ByteOffset<IMAGE_NT_HEADERS>(DosHeader, DosHeader->e_lfanew);
if (IMAGE_NT_SIGNATURE != NtHeader->Signature)
{
MessageBox(0, "Bad NT header signature", "Error", 0);
return false;
}
PIMAGE_EXPORT_DIRECTORY ExportDirectory = ByteOffset<IMAGE_EXPORT_DIRECTORY>(DosHeader,
NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
DWORD* functions = ByteOffset<DWORD>(DosHeader, ExportDirectory->AddressOfFunctions);
for (size_t i = 0; i < ExportDirectory->NumberOfFunctions; ++i)
{
if (functions[i] == (DWORD)old_function - (DWORD)hModule)
{
DWORD oldProtection;
if (!VirtualProtect(functions + i, sizeof(DWORD), PAGE_EXECUTE_READWRITE, &oldProtection))
{
MessageBox(0, "VirtualProtect failed", "Error", 0);
return false;
}
functions[i] = reinterpret_cast<DWORD>(new_function) - reinterpret_cast<DWORD>(DosHeader);
if (!VirtualProtect(functions + i, sizeof(DWORD), oldProtection, &oldProtection))
{
MessageBox(0, "VirtualProtect failed", "Error", 0);
return false;
}
return true;
}
}
return false;
}
bool iat_hook(void* old_function, void* new_function)
{
HMODULE hModule;
DWORD sizeNeeded;
if (0 == EnumProcessModules(GetCurrentProcess(), &hModule, sizeof(hModule), &sizeNeeded))
{
MessageBox(0, "EnumProcessModules failed", "Error", 0);
return false;
}
PIMAGE_DOS_HEADER DosHeader = (PIMAGE_DOS_HEADER)hModule;
PIMAGE_NT_HEADERS NtHeader = ByteOffset<IMAGE_NT_HEADERS>(DosHeader, DosHeader->e_lfanew);
if (IMAGE_NT_SIGNATURE != NtHeader->Signature)
{
MessageBox(0, "Bad NT header signature", "Error", 0);
return false;
}
PIMAGE_IMPORT_DESCRIPTOR ImportDirectory = ByteOffset<IMAGE_IMPORT_DESCRIPTOR>(DosHeader,
NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress);
for (size_t i = 0; ImportDirectory[i].Characteristics; ++i)
{
PIMAGE_THUNK_DATA thunk = ByteOffset<IMAGE_THUNK_DATA>(hModule, ImportDirectory[i].FirstThunk);
PIMAGE_THUNK_DATA origThunk = ByteOffset<IMAGE_THUNK_DATA>(hModule, ImportDirectory[i].OriginalFirstThunk);
for (; origThunk->u1.Function; origThunk++, thunk++)
{
if (thunk->u1.Function == (DWORD)old_function)
{
DWORD oldProtection;
if (!VirtualProtect(&thunk->u1.Function, sizeof(DWORD), PAGE_EXECUTE_READWRITE, &oldProtection))
{
MessageBox(0, "VirtualProtect failed", "Error", 0);
return false;
}
thunk->u1.Function = reinterpret_cast<DWORD>(new_function);
if (!VirtualProtect(&thunk->u1.Function, sizeof(DWORD), oldProtection, &oldProtection))
{
MessageBox(0, "VirtualProtect failed", "Error", 0);
return false;
}
return true;
}
}
}
return false;
}
bool hook(void* old_function, void* new_function)
{
return eat_hook(old_function, new_function) && iat_hook(old_function, new_function);
}
从C ++到德尔福,但我与VAR声明的问题,明确了功能变种。
From c++ to Delp but I'm with problems at var declarations, specifically the "functions" var.
这是我的德尔福转换INCOMPLETE code:
This is my Delphi-converted INCOMPLETE code:
function eat_hook(old_function, new_function:pointer):boolean;
var
Module: HMODULE;
DosHeader: PImageDosHeader;
NtHeaders: PImageNtHeaders;
ExportDirectory: PImageExportDirectory;
functions: PDWORD;
i: size_t;
oldProtection: DWORD;
begin
GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, pointer(old_function), Module);
DosHeader := PImageDosHeader(Module);
NTHeaders := PImageNtHeaders(DWORD(DOSHeader) + DWORD(DOSHeader^._lfanew));
if IMAGE_NT_SIGNATURE <> NtHeaders.Signature then begin
MessageBox(0, 'Bad NT header signature', 'Error', 0);
exit;
end;
ExportDirectory := PImageExportDirectory(PAnsiChar(DosHeader) + NtHeaders.OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
functions := PDWORD(PAnsiChar(DosHeader)+dword(ExportDirectory.AddressOfFunctions));
for i:=0 to ExportDirectory.NumberOfFunctions do begin
if not VirtualProtect(functions, sizeof(dword), PAGE_EXECUTE_READWRITE, @oldProtection) then begin
MessageBox(0, 'VirtualProtect failed', 'Error', 0);
exit;
end;
functions[i] := DWORD(new_function) - DWORD(DosHeader);
if not VirtualProtect(pointer(functions), sizeof(dword), oldProtection, @oldProtection) then begin
MessageBox(0, 'VirtualProtect failed', 'Error', 0);
exit;
end;
end;
end;
它试图要分配给函数[I]
导致编译错误的行:
[DCC Error]: E2016 Array type required
我该如何解决这个问题?
How can I fix this?
推荐答案
您可以采取的事实,即你正在写在顺序和增量数组功能
指针,而不是使用数组索引。
You can take advantage of the fact that you are writing to the array functions
in sequential order and increment the pointer rather than use array indexing.
functions := PDWORD(PAnsiChar(DosHeader)+dword(ExportDirectory.AddressOfFunctions));
for i := 0 to ExportDirectory.NumberOfFunctions-1 do begin
if not VirtualProtect(functions, sizeof(dword), PAGE_EXECUTE_READWRITE, @oldProtection) then begin
MessageBox(0, 'VirtualProtect failed', 'Error', 0);
exit;
end;
functions^ := DWORD(new_function) - DWORD(DosHeader);
if not VirtualProtect(functions, sizeof(dword), oldProtection, @oldProtection) then begin
MessageBox(0, 'VirtualProtect failed', 'Error', 0);
exit;
end;
inc(functions);
end;
这里的诀窍是,每次轮循环功能
指向我在数组中个项。当每一次迭代完成的 INC(功能)
进展到下一个项目的指针,准备下一次迭代。
The trick here is that each time round the loop functions
points to the ith item in the array. When each iteration is done the inc(functions)
advances the pointer on to the next item, ready for the next iteration.
我也纠正了为
循环。在你的Delphi code你执行一个迭代太多了。
I also corrected your for
loop. In your Delphi code you performing one iteration too many.
这篇关于德尔福的问题转换EAT VirtualProtect的挂钩程序从C到德尔福的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!