引发未处理的异常:访问DLL

时间:2020-05-06 15:29:39

标签: c++ winapi process

我正在尝试访问DLL PE文件的dos标头。我从进程的PEB获取IMAGE_DOS_HEADER的地址。我通过访问PEB,然后访问LDR,然后扫描InMemoryOrderModuleList来获取地址,直到找到要访问的DLL(在本例中为kernel32.DLL),并使用dllbase将其转换为IMAGE_DOS_HEADER。获取DLL库后,出现以下错误:

Unhandled exception thrown: read access violation

我的代码:

HMODULE hNtDll = LoadLibraryA("ntdll.dll");
typedef NTSTATUS(NTAPI* pfNtQueryInformationProcess)(HANDLE ProcessHandle, PROCESSINFOCLASS ProcessInformationClass, PVOID ProcessInformation, ULONG ProcessInformationLength, PULONG ReturnLength);
pfNtQueryInformationProcess ntQueryInformationProcess = (pfNtQueryInformationProcess)GetProcAddress(hNtDll, "NtQueryInformationProcess");
PROCESS_BASIC_INFORMATION pBasicInfo;
NTSTATUS status = ntQueryInformationProcess(hProcess, ProcessBasicInformation, &pBasicInfo, sizeof(pBasicInfo), 0);
PPEB peb = pBasicInfo.PebBaseAddress;
PPEB_LDR_DATA ldrData = (PPEB_LDR_DATA)peb->Ldr;
PLIST_ENTRY firstitem_InMemoryOrderModuleList = &ldrData->InMemoryOrderModuleList;
PLIST_ENTRY currentitem_InMemoryOrderModuleList = firstitem_InMemoryOrderModuleList->Flink;
while (true) {
    LDR_DATA_TABLE_ENTRY inMemoryOrderModuleListItem = *(PLDR_DATA_TABLE_ENTRY)currentitem_InMemoryOrderModuleList;
    if (inMemoryOrderModuleListItem.FullDllName.Buffer == NULL) {
        break;
    }
    wcout << inMemoryOrderModuleListItem.FullDllName.Buffer << endl;
    wcout << inMemoryOrderModuleListItem.DllBase << endl;
    PIMAGE_DOS_HEADER dosHeader = (PIMAGE_DOS_HEADER)inMemoryOrderModuleListItem.DllBase;
    if (!wcscmp(inMemoryOrderModuleListItem.FullDllName.Buffer, L"KERNEL32.DLL")) {
        PIMAGE_DOS_HEADER dosHeader = (PIMAGE_DOS_HEADER)(inMemoryOrderModuleListItem.DllBase);
        cout << "-------------------------" << endl;
        PIMAGE_NT_HEADERS ntHeader = (PIMAGE_NT_HEADERS)((DWORD_PTR)dosHeader + dosHeader->e_lfanew); // error on this line because trying to access the dosHeader
    }
    currentitem_InMemoryOrderModuleList = currentitem_InMemoryOrderModuleList->Flink;
}

1 个答案:

答案 0 :(得分:1)

您的currentitem_InMemoryOrderModuleList只是指向 LIST_ENTRY。而这个LIST_ENTRYInMemoryOrderLinks。您可以调整指针以指向封闭 使用前的结构。

请参阅“ PEB (Process Environment Block) invalid DllBase address”,“ CONTAINING_RECORD”(根据结构的类型和包含结构中字段的地址,返回结构实例的基地址。)

以下代码对我有用。您可以尝试:

LDR_DATA_TABLE_ENTRY