DWORD MappedPeFile::getIatVa(const char *module, const char *name) { for (PIMAGE_IMPORT_DESCRIPTOR imp = (PIMAGE_IMPORT_DESCRIPTOR)((DWORD)m_pDOS + rva2FileOffset(m_pNT->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress)); imp->Characteristics != 0; imp++) { const char *szModule = (const char*)((DWORD)m_pDOS + rva2FileOffset(imp->Name)); if (stricmp(module, szModule) != 0) { continue; } for (PIMAGE_THUNK_DATA originalThunk = (PIMAGE_THUNK_DATA)((DWORD)m_pDOS + rva2FileOffset(imp->OriginalFirstThunk)), firstThunk = (PIMAGE_THUNK_DATA)((DWORD)m_pDOS + rva2FileOffset(imp->FirstThunk)); originalThunk->u1.Function != 0; originalThunk++, firstThunk++) { if (originalThunk->u1.Function & IMAGE_ORDINAL_FLAG32) { if ((DWORD)name == IMAGE_ORDINAL32(originalThunk->u1.Function)) { return ptr2va(&firstThunk->u1.Function); } } else { const char *importName = (const char*)((PIMAGE_IMPORT_BY_NAME)((DWORD)m_pDOS + rva2FileOffset(originalThunk->u1.AddressOfData)))->Name; if (!stricmp(name, importName)) { return ptr2va(&firstThunk->u1.Function); } } } } return 0; }
FARPROC PatchImportOld(char* sourceModule, char* importModule, LPCSTR name, void* patchFunction) { if ( !name ) return NULL; HMODULE tempModule = GetModuleHandleA(sourceModule); if ( !tempModule ) return NULL; IMAGE_THUNK_DATA32* importOrigin = _GetImportsList(sourceModule, importModule); if ( !importOrigin ) return NULL; DWORD* importFunction = _GetFunctionsList(sourceModule, importModule); if ( !importFunction ) return NULL; for (u32 i = 0; importOrigin[i].u1.Ordinal != 0; i++) { if (IMAGE_SNAP_BY_ORDINAL32(importOrigin[i].u1.Ordinal) && (DWORD)name < 0xFFFF) { if (IMAGE_ORDINAL32(importOrigin[i].u1.Ordinal) == IMAGE_ORDINAL32((DWORD)name)) { FARPROC oldFxn = (FARPROC)importFunction[i]; WriteMem(&importFunction[i], &patchFunction, 4); return oldFxn; } } else { #pragma warning(suppress: 6387) if (_strcmpi(name, (const char*)((PIMAGE_IMPORT_BY_NAME)((u32)importOrigin[i].u1.AddressOfData + (u32)tempModule))->Name) == 0) { FARPROC oldFxn = (FARPROC)importFunction[i]; WriteMem(&importFunction[i], &patchFunction, 4); return oldFxn; } } } return NULL; }
//============================================================================== bool PEFile::readImportTable() { DWORD tableRVA = peHeaders.OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress; DWORD tableOffset = rvaToOffset(tableRVA); if (tableOffset == 0) { return false; } ZeroMemory(&importTable, sizeof(PE_IMPORT_DLL)); IMAGE_IMPORT_DESCRIPTOR* importDesc = (IMAGE_IMPORT_DESCRIPTOR*)(peMemory + tableOffset); IMAGE_THUNK_DATA* importThunk; PE_IMPORT_DLL* importDll = &this->importTable; PE_IMPORT_FUNCTION* importFunction; while (true) { importDll->DllName = (char*)(peMemory + rvaToOffset(importDesc->Name)); if (importDesc->OriginalFirstThunk > 0) { importThunk = (IMAGE_THUNK_DATA*)(peMemory + rvaToOffset(importDesc->OriginalFirstThunk)); } else { importThunk = (IMAGE_THUNK_DATA*)(peMemory + rvaToOffset(importDesc->FirstThunk)); } importDll->Functions = new PE_IMPORT_FUNCTION(); ZeroMemory(importDll->Functions, sizeof(PE_IMPORT_FUNCTION)); importFunction = importDll->Functions; while (true) { if ((importThunk->u1.Ordinal & IMAGE_ORDINAL_FLAG32) == IMAGE_ORDINAL_FLAG32) { importFunction->FunctionId = IMAGE_ORDINAL32(importThunk->u1.Ordinal); } else { DWORD nameOffset = rvaToOffset(importThunk->u1.AddressOfData); importFunction->FunctionName = (char*)(peMemory + nameOffset + 2); } importThunk = (IMAGE_THUNK_DATA*)((char*)importThunk + sizeof(IMAGE_THUNK_DATA)); if (importThunk->u1.AddressOfData == 0) { break; } importFunction->Next = new PE_IMPORT_FUNCTION(); ZeroMemory(importFunction->Next, sizeof(PE_IMPORT_FUNCTION)); importFunction = importFunction->Next; } importDesc = (IMAGE_IMPORT_DESCRIPTOR*)((char*)importDesc + sizeof(IMAGE_IMPORT_DESCRIPTOR)); if (importDesc->Name == 0) { break; } importDll->Next = new PE_IMPORT_DLL(); ZeroMemory(importDll->Next, sizeof(PE_IMPORT_DLL)); importDll = importDll->Next; } return true; }
HRESULT PE_PrintImport(PBYTE pBase, IMAGE_DATA_DIRECTORY DataImport, BOOL bImport) { HRESULT result = S_OK; PIMAGE_IMPORT_DESCRIPTOR pImportBlack = NULL; PIMAGE_THUNK_DATA32 pFirstThunkData32 = NULL; PIMAGE_THUNK_DATA32 pOriginalThunkData32 = NULL; PIMAGE_IMPORT_BY_NAME pImageImportByName = NULL; pImportBlack = PIMAGE_IMPORT_DESCRIPTOR(pBase + DataImport.VirtualAddress); if (!pImportBlack || !DataImport.Size) { dprintf("没有导入表 \n"); return S_OK ; } char *pDllName = NULL; if (bImport) { while (pImportBlack->Name != 0 && pImportBlack->Characteristics != 0) { pFirstThunkData32 = (PIMAGE_THUNK_DATA32)((ULONG)pBase + (ULONG)(pImportBlack->FirstThunk)); pOriginalThunkData32 = (PIMAGE_THUNK_DATA32)((ULONG)pBase + (ULONG)(pImportBlack->OriginalFirstThunk)); pDllName = (PCHAR)((ULONG_PTR)pBase + (ULONG_PTR)pImportBlack->Name); dprintf("DLL name is %s\n", pDllName); dprintf("序号 相对偏移 函数地址 函数名称 \n"); while (pOriginalThunkData32->u1.Ordinal != 0) { if (IMAGE_SNAP_BY_ORDINAL32(pOriginalThunkData32->u1.Ordinal)) { dprintf("%04d 0x%08x 0x%08x 无\n", IMAGE_ORDINAL32(pOriginalThunkData32->u1.Ordinal), (ULONG_PTR)pOriginalThunkData32 - (ULONG_PTR)pBase, *pFirstThunkData32); } else { pImageImportByName = (PIMAGE_IMPORT_BY_NAME)((UCHAR*)pBase + pOriginalThunkData32->u1.AddressOfData); dprintf("%04d 0x%08x 0x%08x %s\n", pImageImportByName->Hint, (ULONG_PTR)pOriginalThunkData32->u1.AddressOfData, *pFirstThunkData32, pImageImportByName->Name); } pOriginalThunkData32++; pFirstThunkData32++; } pImportBlack++; } } return result; }