我需要區分一個32位PE從16位DOS MZ。 做什麼是正確的方法? 我可以使用啓發式查找PE標頭,但我覺得它不一定是確定性的如何diffrentiate 16位MZ和32位MZ
回答
所有DOS樣式的可執行文件都有'MZ'作爲前兩個字節。
要識別MSDOS可執行文件與其他衆多變體,最好的辦法似乎是讀取文件中偏移量爲0x0018的重定位表的位置,如果該位置大於0x0040(進入文件),則不僅僅是普通的DOS。
爲了將可執行文件明確標識爲'PE'可執行文件,文件中的偏移量0x003C處有一個指針。這是文件內的一個偏移量,它將包含字節「PE」和兩個字節。其他MSDOS'MZ'變體將使用相同的位置來放置其他代碼,例如'NE','W3','LE'等。
'PE'風格的可執行文件也有很多種形式,我希望你會至少對32位和64位感興趣。
也許這類事情的最終權威是Unix的'文件'命令,它的目的是通過調查它的內容來可靠地識別任何文件類型。 MSDOS部分列出了here。微軟並不是一個可靠的機構,因爲他們忽略了非微軟的信息。
普通的DOS EXE頭只有28(0x1C
)個字節長,通常在DOS重定位表後面會出現。 NT PE標頭的IMAGE_DOS_HEADER
struct
在64(0x40)字節處大得多,因爲它已被擴展用於各種其他Windows可執行格式。這個頭的大小不同是爲什麼@ user3710044的答案不僅是最快的,而且是可靠的:如果重定位表[e_lfarlc] < 0x40),EXE就是普通的DOS。
只要你意識到在普通的DOS可執行文件中不存在e_lfanew
成員(一些可能的「擴展」頭文件的偏移量),還可以使用以下邏輯來區分各種MZ樣式格式:
如果文件的開頭並非以「MZ」或「ZM」開頭,則它不是DOS或Windows可執行映像。否則,您可能有以下類型的可執行格式之一:普通DOS,NE(Windows 16位),LE(16位VXD),PE32或PE32 +(PE64)。
通過查看
e_lfanew
值,確定您是否擁有普通的DOS可執行文件。普通的DOS可執行文件將有一個超出範圍e_lfanew
指向文件限制之外的零,或者如果偏移恰好在範圍內,則其偏移處的簽名將不匹配下面的任何簽名。"PE" followed by two zero bytes if the image is a PE32 or PE32+ (PE64) and is further determined by the "magic" in the NT Optional Header "NE" indicates the image is a 16-bit Windows executable "LE" indicates the image is a 16-bit Virtual Device Driver (VXD)
更多晦澀簽名(從Ralph Brown's INT 21/AH=4Bh引用)::
嘗試通過e_lfanew
具有以下WORD或DWORD值匹配的「範圍內」偏移指向的簽名
LX variant of LE used in OS/2 2.x
W3 Windows WIN386.EXE file; a collection of LE files
W4 Windows95 VMM32.VXD file
DL HP 100LX/200LX system manager compliant executable (.EXM)
MP old PharLap .EXP
P2 PharLap 286 .EXP
P3 PharLap 386 .EXP
- 1. 位NASM 16和位32
- 2. SIZEOF指針16位和32位
- 3. VBA錯誤處理和MZ工具
- 4. 確定MZ EXE結束的位置,並且LE/LX/PE開始
- 5. 在MZ(DOS,16位).EXE標頭中的頁數和最後一頁大小的重要性
- 6. 16位的int VS 32位的int和64位INT
- 7. 將16位轉換爲32位浮點
- 8. 16位圖像轉換爲32位
- 9. Python將32位轉換爲16位tiff
- 10. 8位微處理器上的C - 32位和16位算術
- 11. Z3Py:我應該如何表示一些32位; 16位和8位寄存器?
- 12. 重新定義的Mz從ZAP-到炭
- 13. 如何在C#中將16位'short'轉換爲32位整數?
- 14. 將12位int轉換爲16位或32位
- 15. C 8位16位32位編譯器之間的區別
- 16. 什麼數據類型是32位操作系統中的16位和64位操作系統中的32位?
- 17. 從C語言地址讀取8位或16位或32位
- 18. 如何從32位/ 24位從字節到16位轉換爲字節
- 19. 如何轉換位圖圖像的32位到16位色彩質量在C#
- 20. 如何將Zebra MZ-220打印機連接到Symbol MC-7095?
- 21. 16位位深
- 22. 32位和64位CPU/OS
- 23. C# - 在32位和64位
- 24. 在32位和64位
- 25. 32位訪問和32位Java
- 26. 32位和64位的ODP.NET
- 27. Java 32位和64位
- 28. Gluegen 32位和64位庫
- 29. Python和16位PGM
- 30. ODBC .NET 32位和64位
這不是「只是一個啓發式」。所有的可執行文件都有一個16位的加載程序,而對於32位(也可以是LE)的頭文件,它提供了必要的信息。其他操作系統如何知道? – usr2564301 2015-03-02 07:27:33