0

自分のプロセスへの IAT フックについて質問したいのですが。

現在、ExitProcess をフックして、ExitProcess 呼び出しの前に特定の関数を実行しようとしていますが、いくつかの問題に直面しています。

実行時に PE をトラバースし、 IMAGE_IMPORT_DESCRIPTOR を通過し、kernel32.dll (最初の .dll) を見つけた後、THUNK_DATA-s を名前でトラバースし、そこに ExitProcess を見つけようとしていますが、運はありません。

関数のログ、それらはそこにある関数です -

GetModuleHandleA
GetProcAddress
LoadLibraryA
GetModuleFileNameW
FreeLibrary
VirtualQuery
GetProcessHeap
HeapFree
HeapAlloc
GetSystemTimeAsFileTime
GetCurrentThreadId
GetCurrentProcessId
QueryPerformanceCounter
IsProcessorFeaturePresent
WideCharToMultiByte
MultiByteToWideChar
LoadLibraryW
lstrlenA
LoadLibraryExW
GetLastError
RaiseException
IsDebuggerPresent
DecodePointer
EncodePointer
GetModuleHandleW

ExitProcess は 内のどこにもありませんが。

同様に失敗しましたが、名前の代わりに関数ポインターで列挙しようとしました(originalthunkdataの代わりにthunkdataを使用)。

ExitProcess の GetProcAddress は PE 内のポインターを返します。結果は同じですが、loadlibrary によって強制的に (自動的に読み込まれるはずですが) kernel32.dll を読み込もうとしました。

何が問題なのですか?

HMODULE hMod = GetModuleHandle(NULL);
PIMAGE_DOS_HEADER pImgDosHeaders = (PIMAGE_DOS_HEADER)hMod;
PIMAGE_NT_HEADERS pImgNTHeaders = (PIMAGE_NT_HEADERS)((LPBYTE)pImgDosHeaders + pImgDosHeaders->e_lfanew);
PIMAGE_IMPORT_DESCRIPTOR pImgImportDesc = (PIMAGE_IMPORT_DESCRIPTOR)((LPBYTE)pImgDosHeaders + pImgNTHeaders->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress);
UINT indx = 0;
while(strcmpi((PCHAR)((LPBYTE)pImgDosHeaders + pImgImportDesc[indx].Name), "kernel32.dll")) { ++indx; };
PIMAGE_THUNK_DATA pImgThunkData = (PIMAGE_THUNK_DATA)((LPBYTE)pImgDosHeaders +pImgImportDesc[indx].OriginalFirstThunk);
PIMAGE_IMPORT_BY_NAME pImgImportByName = NULL;
for(;pImgThunkData->u1.Function; ++pImgThunkData)
{
    pImgImportByName = (PIMAGE_IMPORT_BY_NAME)((LPBYTE)pImgDosHeaders + pImgThunkData->u1.AddressOfData);
    !strcmpi("ExitProcess",pImgImportByName->Name) ? cout << "ExitProcess Found" : false;
}
return true;

どうもありがとうございました。素晴らしい一日を!

4

1 に答える 1

0

アプリがExitProcess()静的に呼び出されない場合 (アプリの RTL によっても呼び出されない場合)、または を介し​​て動的に読み込まれる場合などGetProcAddress()、アプリの IMPORTS テーブルには存在しません。IMPORTS テーブルには、アプリが静的にリンクする関数のみが一覧表示されます。これが、コードが見つからない理由である可能性があります。PEDUMP や DependancyWalker などのユーティリティを使用して、アプリが実際に静的にリンクしていることを確認しますExitProcess()。たとえば、私の開発環境 (C++Builder XE2) では、コンソール プロジェクトを作成するExitProcess()と IMPORTS テーブルに見つかりませんが、代わりに GUI プロジェクトを作成すると見つかります。違いは、2 つのタイプのプロジェクトが内部で異なる RTL を使用ExitProcess()することです。そのため、アプリの終了時にコンソール RTL が使用されないようです。

于 2013-02-11T06:40:13.537 に答える