我在嘗試讀取PE文件。
問題是,數據使用RVA指針,而我需要在文件
內偏移來獲得我所需要的。 如何將RVA轉換爲文件中的偏移量?從RVA獲得文件偏移
回答
,以確定文件的RVA偏移,您需要:
- ,以確定其中部分點RVA。從部分
- 的地址相對虛擬地址
- 減增加導致文件部分
,您會收到一個文件偏移量,你需要的偏移。
file Offset = RVAOfData - Virtual Offset + Raw Offset
例子:
我們的資源部分( 「.rsrc」)的詳細信息:
虛擬偏移:F000
原始偏移:C600
讓我們看看在資源上的一個我們有:
名稱:BIN
數據 RVA:F0B0
文件偏移量:?
fileOffset = RVAOfData - Virtual Offset + Raw Offset
=> C6B0 = F0B0 - F000 + C600
文件偏移量:C6B0
參考:
Understanding RVAs and Import Tables - by Sunshine
在C#功能:
// Example:
// RVA: F0B0
// Virtual offset: F000 ("RVA" in PEview)
// Raw offset: C600 ("Pointer to Raw Data" in PEview)
// fileOffset = F0B0 - F000 + C600 = C6B0
private static uint rvaToFileOffset(uint i_Rva, uint i_VirtualOffset, uint i_RawOffset)
{
return (i_Rva - i_VirtualOffset + i_RawOffset);
}
下面的例子給出了來自RVA的入口點地址的文件偏移量。可以傳遞任何指針以從RVA獲取其磁盤偏移量。
基本上我們需要找到地址屬於哪個部分。一旦確定了正確的部分,使用下面的公式來獲得偏移量。
DWORD retAddr = PTR - (sectionHeader->其VirtualAddress)+
(sectionHeader->的PointerToRawData);
然後添加文件基地址來獲得物理地址
retAddr +(PBYTE)lpFileBase
LPCSTR fileName="exe_file_to_parse";
HANDLE hFile;
HANDLE hFileMapping;
LPVOID lpFileBase;
PIMAGE_DOS_HEADER dosHeader;
PIMAGE_NT_HEADERS peHeader;
PIMAGE_SECTION_HEADER sectionHeader;
hFile = CreateFileA(fileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0);
if(hFile==INVALID_HANDLE_VALUE)
{
printf("\n CreateFile failed in read mode \n");
return 1;
}
hFileMapping = CreateFileMapping(hFile,NULL,PAGE_READONLY,0,0,NULL);
if(hFileMapping==0)
{
printf("\n CreateFileMapping failed \n");
CloseHandle(hFile);
return 1;
}
lpFileBase = MapViewOfFile(hFileMapping,FILE_MAP_READ,0,0,0); // Base pointer to file
if(lpFileBase==0)
{
printf("\n MapViewOfFile failed \n");
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
dosHeader = (PIMAGE_DOS_HEADER) lpFileBase; //pointer to dos headers
if(dosHeader->e_magic==IMAGE_DOS_SIGNATURE)
{
//if it is executable file print different fileds of structure
//dosHeader->e_lfanew : RVA for PE Header
printf("\n DOS Signature (MZ) Matched");
//pointer to PE/NT header
peHeader = (PIMAGE_NT_HEADERS) ((u_char*)dosHeader+dosHeader->e_lfanew);
if(peHeader->Signature==IMAGE_NT_SIGNATURE)
{
printf("\n PE Signature (PE) Matched \n");
// valid executable so we can proceed
//address of entry point
DWORD ptr = peHeader->OptionalHeader.AddressOfEntryPoint;
//instead of AEP send any pointer to get actual disk offset of it
printf("\n RVA : %x \n",ptr); // this is in memory address i.e. RVA
//suppose any one wants to know actual disk offset of "address of entry point" (AEP)
sectionHeader = IMAGE_FIRST_SECTION(peHeader); //first section address
UINT nSectionCount = peHeader->FileHeader.NumberOfSections;
UINT i=0;
//check in which section the address belongs
for(i=0; i<=nSectionCount; ++i, ++sectionHeader)
{
if((sectionHeader->VirtualAddress) > ptr)
{
sectionHeader--;
break;
}
}
if(i>nSectionCount)
{
sectionHeader = IMAGE_FIRST_SECTION(peHeader);
UINT nSectionCount = peHeader->FileHeader.NumberOfSections;
for(i=0; i<nSectionCount-1; ++i,++sectionHeader);
}
//once the correct section is found below formula gives the actual disk offset
DWORD retAddr = ptr - (sectionHeader->VirtualAddress) +
(sectionHeader->PointerToRawData);
printf("\n Disk Offset : %x \n",retAddr+(PBYTE)lpFileBase);
// retAddr+(PBYTE)lpFileBase contains the actual disk offset of address of entry point
}
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
//getchar();
return 0;
}
else
{
printf("\n DOS Signature (MZ) Not Matched \n");
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
你可以給你的代碼添加一些評論嗎? – 2018-01-15 12:40:07
添加了一些說明以及評論。 – 2018-01-15 13:28:40
- 1. 偏移和RVA之間的區別
- 2. DUMPBIN文件偏移
- 3. 從jquery獲取偏移值
- 4. 試圖從lipo獲得偏移會產生非胖文件錯誤
- 5. 如何知道偏移量如何從大文件中獲得一行
- 6. LoadLibrary從文件中的偏移量
- 7. 如何獲得__TIME__的UTC偏移量?
- 8. 獲得UTC的日期時間偏移
- 9. 如何獲得時區偏移值
- 10. 如何獲得時區偏移爲±hh:mm?
- 11. 如何獲得kafka的最新偏移
- 12. 如何在logstash中獲得偏移量?
- 13. C# - 從已知偏移量的文件中獲取字節
- 14. 我可以從Unix命令行獲得UTC偏移量嗎?
- 15. 歌劇返回偏移自動如何獲得實際的偏移號碼?
- 16. 從偏移量中選擇一部分數據從偏移量到偏移量
- 17. ImageMagick從中心偏移文本
- 18. 從文件名獲得mimetype
- 19. 如何從pdf文檔獲取字符偏移信息?
- 20. 從onBefore更改偏移 - LocalScroll jQuery插件
- 21. 獲取精靈節偏移
- 22. codeigniter獲取時區偏移
- 23. 從文件名獲得文件路徑
- 24. 如何獲取python文件中的字節偏移量
- 25. Paser符號(pdb)文件並獲取函數名稱和偏移
- 26. 內存映射文件偏移量低
- 27. NSURLSessionUploadTask偏移文件上傳上重試
- 28. Python基於偏移量寫入文件
- 29. 內存偏移彙編列表文件
- 30. 更改geotiff文件的偏移量
假如你不能從文件中讀取它,如何做PE裝載器工作? – harold 2012-03-31 12:18:25
我不知道...它顯示的是放鬆信息嗎?如果我可以從文件中讀取它,那麼地址偏移量是多少? – Idov 2012-03-31 12:21:52
根據我的信息,他們是相對於ImageBase(在標題中) – harold 2012-03-31 12:28:54