其他语言

本类阅读TOP10

·基于Solaris 开发环境的整体构思
·使用AutoMake轻松生成Makefile
·BCB数据库图像保存技术
·GNU中的Makefile
·射频芯片nRF401天线设计的分析
·iframe 的自适应高度
·BCB之Socket通信
·软件企业如何实施CMM
·入门系列--OpenGL最简单的入门
·WIN95中日志钩子(JournalRecord Hook)的使用

分类导航
VC语言Delphi
VB语言ASP
PerlJava
Script数据库
其他语言游戏开发
文件格式网站制作
软件工程.NET开发
探密PE文件格式(Portable Executable File Format)(上)

作者:未知 来源:月光软件站 加入时间:2005-5-13 月光软件站

开篇语:
本文只是我学习PE过程中的一些学习笔记,没有什么技术含量。:) 
PE格式是WINDOWS下最常用的可执行文件格式。本文将用win32汇编进行描述。

------------------------------
|      IMAGE_DOS_HEADER      |  <-------DOS MZ 文件头
------------------------------
|        DOS    STUB         |  <-------DOS可分行代码块
------------------------------
|     IMAGE_NT_HEADERS       |  <-------PE文件头
------------------------------
|      SECTION  TABLE        |  <-------节表
------------------------------
|          SECTION           |  <-------节
------------------------------
|          SECTION           |
------------------------------
|            ...             |
------------------------------      
        PE文件格式一览

上图就是PE文件的基本结构,在PE文件中,代码、数据、资源什么的依据不同的属性而被存放到不同的SECTION(节)中,而每个SECTION的属性和位置等信息用一个IMAGE_SECTION_HEADER结构来描述,所有的IMAGE_SECTION_HEADER结构组成一个SECTION TABLE(节表)。
纵观PE格式,我们可以发现一个PE文件分为两大块:DOS部分(DOS文件头+DOS块)+WIN32部分(PE文件头+节表+节)

DOS部分
MZ格式的文件头(IMAGE_DOS_HEADER)和可执行代码(DOS STUB)组成了DOS部分。MZ格式的DOS文件头是由IMAGE_DOS_HEADER结构定义的:

IMAGE_DOS_HEADER  STRUCT
e_magic	word	?	;00000000 DOS可执行文件标记,为"MZ",在Windows.inc中预定义为IMAGE_DOS_SIGNATURE。
e_cblp		word	?
e_cp		word	?
e_crlc		word	?
e_cparhdr	       word	?
e_minalloc	word	?
e_maxalloc	word	?
e_ss		word	?
e_sp		word	?
e_csum		word	?
e_ip		word	?
e_cs		word	?
e_lfarlc	             word	?
e_ovno		word	?
e_res		word	4 dup(?)
e_oemid	             word	?
e_oeminfo	       word	?
e_res2		word	10 dup(?)
e_lfanew	            dword	?	;0000003ch 指向PE文件头,以此来引出PE文件头

一般我们只关心e_magic和e_lfanew这两个字段的值。而e_lfanew这个字段的值在这个结构中是最重要的。DOS的可执行代码部分(DOS STUB)一般只是简单的显示一句"This program connot be run in DOS mode."有的是"This program requires win32."这些代码一般是编译器自动完成的,当然我们也可以定制DOS STUB部分,只要在link时使用/stub:dos_file_name.exe选项进行链接就可以了。

:) 实践是检验真理的标准。

-----------------------------cut-----------------------------------
.386
.model flat,stdcall
option casemap:none

include		windows.inc
include		user32.inc
include		kernel32.inc
includelib		user32.lib
includelib		kernel32.lib

.data
szCaption	db	'wensir!',0
szText		db	'Hello World!',0

.code
start:
	invoke MessageBox,NULL,offset szText,offset szCaption,MB_OK
	invoke ExitProcess,NULL
	end start
---------------------------cut---------------------------------------

保存为*.asm,我这里保存为wensir.asm,然后编译之:
ml /c /coff wensir.asm
link /subsystem:windows wensir.obj
现在我们得到一个简单的"Hello World"的win32程序wensir.exe,当然,它是PE格式的。随便到哪里DOWN一个16进制编辑器来,我用的是UltraEdit,将wensir.exe用16进制编辑器打开:

----------------------------------------------------------------------------
           0  1  2  3  4   5  6  7  8  9  A  B  C  D  E  F    
00000000h: 4D 5A 90 00 03 00 00 00 04 00 00 00 FF FF 00 00 ; MZ?........��..
00000010h: B8 00 00 00 00 00 00 00 40 00 00 00 00 00 00 00 ; ?......@.......
00000020h: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ; ................
00000030h: 00 00 00 00 00 00 00 00 00 00 00 00 B0 00 00 00 ; ............?..
00000040h: 0E 1F BA 0E 00 B4 09 CD 21 B8 01 4C CD 21 54 68 ; ..?.???L?Th
00000050h: 69 73 20 70 72 6F 67 72 61 6D 20 63 61 6E 6E 6F ; is program canno
00000060h: 74 20 62 65 20 72 75 6E 20 69 6E 20 44 4F 53 20 ; t be run in DOS 
00000070h: 6D 6F 64 65 2E 0D 0D 0A 24 00 00 00 00 00 00 00 ; mode....$.......
00000080h: 5D 65 FD C8 19 04 93 9B 19 04 93 9B 19 04 93 9B ; ]e..摏..摏..摏
00000090h: 97 1B 80 9B 11 04 93 9B E5 24 81 9B 18 04 93 9B ; ??.摏?仜..摏
000000a0h: 52 69 63 68 19 04 93 9B 00 00 00 00 00 00 00 00 ; Rich..摏........
000000b0h: 50 45 00 00 4C 01 03 00 1C 8C 45 42 00 00 00 00 ; PE..L....孍B....
........
-----------------------------------------------------------------------------

00000000h处的5A4D便是IMAGE_DOS_HEADER中e_magic字段的值"MZ",0000003ch处的值0000000bh值是e_lfanew,它指向PE文件头的位置。从00000040h-000000a0便是DOS STUB块,从上图中我们可以看到"This program cannot be run in dos mode"字样。

重头戏在WIN32部分。:) 欲知后事如何,请听下回分解。



相关文章

相关软件