📄 29a-7.023
字号:
Let's take a look at our hello.EXE file and especially at the OPTIONAL
HEADER:
Physical
offset 0 1 2 3 4 5 6 7 8 9 A B C D E F
00000080 0B 01 00 00 00 00 00 00 ........
00000090 00 00 00 00 00 00 00 00 00 10 00 00 00 00 00 00 ................
000000A0 00 00 00 00 00 00 40 00 00 10 00 00 00 02 00 00 ................
000000B0 01 00 00 00 00 00 00 00 04 00 00 00 00 00 00 00 ................
000000C0 00 50 00 00 00 04 00 00 00 00 00 00 02 00 00 00 ................
000000D0 00 00 10 00 00 10 00 00 00 00 10 00 00 10 00 00 ................
000000E0 00 00 00 00 10 00 00 00 00 00 00 00 00 00 00 00 ................
000000F0 00 30 00 00 94 00 00 00 00 00 00 00 00 00 00 00 ................
00000100 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
00000110 00 40 00 00 18 00 00 00 00 00 00 00 00 00 00 00 ................
00000120 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
00000130 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
00000140 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
00000150 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
00000160 00 00 00 00 00 00 00 00 ........
-At offset 000000A4h is the IMAGE BASE: this value is 00400000h
So the file will be loaded in memory at 00400000h
-At offset 000000A8h is the OBJECT ALIGN value: 00001000h. All section will
be loaded at an offset which is a power of this value.
-At offset 000000ACh is the File ALIGN value: 00000200h. All section are
written (on disk) at an offset which is a power of this value.
-At offset 000000F0h is the IMPORT TABLE RVA value: 00003000h. So the IMPORT
TABLE begin at offset 00403000h on memory (IMAGE BASE+RVA) We will take a
look at IMPORT TABLE later...
****************
* OBJECT TABLE *
****************
The number of entries in the Object Table is set by the # Objects field in
the PE Header. Entries in the Object Table are numbered starting from one.
The Object Table immediately follows the PE OPIONAL HEADER. The order and the
name of the object are chosen by the linker. The RVA for objects must be
assigned by the linker such that they are in ascending order and adjacent,
and must be a multiple of Object Align set in the PE header. Each Object
Table entry has the following format:
+---------------------------------------------------+
| OBJECT NAME |
+-------------------------+-------------------------+
| VIRTUAL SIZE | RVA |
+-------------------------+-------------------------+
| PHYSICAL SIZE | PHYSICAL OFFSET |
+-------------------------+-------------------------+
| RESERVED | RESERVED |
+-------------------------+-------------------------+
| RESERVED | OBJECT FLAGS |
+-------------------------+-------------------------+
OBJECT NAME : Object name. This is an eight-byte, null-padded ASCII string
representing the object name.
VIRTUAL SIZE : Virtual memory size. The size of the object that will be
allocated when the object is loaded. Any difference between
Physical Size and Virtual Size is zero filled.
It is the size of the section after being load on memory.
RVA : Relative Virtual Address. This is the virtual address that the
object is currently relocated to relative to the Image Base.
Each Object's virtual address space consumes a multiple of
Object Align (power of 2 between 512 and 256M inclusive. The
default is 64K.), and immediately follows the previous Object
in the virtual address space (the virtual address space for an
image must be dense).
PHYSICAL SIZE : Physical file size of the section. The size of the
section in the file for the object. The physical size
must be a multiple of the File Align field in the PE Header,
and must be less than or equal to the Virtual Size.
PHYSICAL OFFSET : Physical offset for the object's first page. This offset is
relative to the beginning of the EXE file, and is aligned on a
multiple of the File Align field in the PE Header. The offset
is used as a seek value.
OBJECT FLAGS : Flag bits for the object. The object flag bits have the
following definitions:
Flag Definition
000000008h Section should not be padded to next boundary. This
is obsolete and replaced by IMAGE_SCN_ALIGN_1BYTES.
This is valid for object files only.
000000020h Code object
000000040h Initialized data object
000000080h Uninitialized data object
000000200h Section contains comments or other information. The
.drectve section has this type. This is valid for
object files only.
000000800h Section will not become part of the image. This is
valid for object files only.
000001000h Section contains COMDAT data.
000100000h Align data on a 1-byte boundary. valid for object
files only.
000200000h Align data on a 2-byte boundary.
000300000h Align data on a 4-byte boundary.
000400000h Align data on a 8-byte boundary.
000500000h Align data on a 16-byte boundary.
000600000h Align data on a 32-byte boundary.
000700000h Align data on a 64-byte boundary.
000800000h Align data on a 128-byte boundary.
000900000h Align data on a 256-byte boundary.
000A00000h Align data on a 512-byte boundary.
000B00000h Align data on a 1024-byte boundary.
000C00000h Align data on a 2048-byte boundary.
000D00000h Align data on a 4096-byte boundary.
000E00000h Align data on a 8192-byte boundary.
001000000h Section contains extended relocations.
002000000h Section can be discarded as needed.
040000000h Object must not be cached
080000000h Object is not pageable
100000000h Object is shared
200000000h Executable object
400000000h Readable object
800000000h Writeable object
All other bits are reserved for future use
and should be set to zero.
Take a look one more time at our HELLO.EXE file
Physical
offset 0 1 2 3 4 5 6 7 8 9 A B C D E F
00000160 43 4F 44 45 00 00 00 00 CODE....
00000170 00 10 00 00 00 10 00 00 3A 00 00 00 00 04 00 00 ................
00000180 00 00 00 00 00 00 00 00 00 00 00 00 60 00 00 60 ................
00000190 49 4D 50 4F 52 54 53 00 00 10 00 00 00 20 00 00 IMPORTS.........
000001A0 0C 00 00 00 00 06 00 00 00 00 00 00 00 00 00 00 ................
000001B0 00 00 00 00 60 00 00 60 69 6D 70 6F 72 74 73 00 ........imports.
000001C0 00 10 00 00 00 30 00 00 94 00 00 00 00 08 00 00 ................
000001D0 00 00 00 00 00 00 00 00 00 00 00 00 40 00 00 50 ................
000001E0 72 65 6C 6F 63 73 00 00 00 10 00 00 00 40 00 00 relocs..........
000001F0 18 00 00 00 00 0A 00 00 00 00 00 00 00 00 00 00 ................
00000200 00 00 00 00 40 00 00 52 ........
-At offset 00000168h is the name of the first OBJECT TALBE: "CODE",0,0,0,0
With such a name we can easy deduce that it is the code section.
-At offset 00000174h is the RVA of this section: 00001000h. So the code
section will be loaded at offset 00401000h on memory (IMAGE BASE + RVA)
-At offset 0000017Ch is the PHYSICAL OFFSET: 00000400h. So this section is
writen on file at 00000400h (relative to the the beginning of the file)
-At offset 0000018Ch are the FLAGS: 60000060h
60000060h = 000000020h + 000000040h + 200000000h + 400000000h
| | | |
Code object <----+ | | |
Initialized data object <-----+ | |
Executable object <-----------------------+ |
Readable object <-------------------------------------+
******************
* IMPORT SECTION *
******************
The most difficult thing to understood in coding a win32 virus is the IMPORT
section: All APIs (like MessageBoxA, ExitProcess,...) are in some .DLL files
For example MessageBoxA is in user32.dll and ExitProcess is in kernel32.dll.
Before to run hello.exe, the import section contain all the APIs name and the
name of the .DLL used in hello.exe .When you run hello.exe file, the loader
write at the right place (in import section) the address of the APIs (entry
point in the .DLL files). Why a such thing??? because the .DLL file can be
loaded at different address ( at the image base; note that image base value
is only a suggested address). So the problem for us is that kernel32.dll is
not always at the same place (see different version of windows: 95, 98, 2000,
NT, ...) And the entry point of APIs are not at the same place...CLEAR ???
There is two ways to IMPORT APIs address in an PE .EXE file: by hint and by
ordinal. But there is only one way to EXPORT APIs address in a .DLL file: by
ordinal
I will try now to explain the concept of the IMPORT section (by hint):
The IMPORT section (by hint) begin with the IMPORT DATA DIRECTORYs. A IMPORT
DATA DIRECTORY is relative to only one .DLL After it is put data: .DLL name
,list of pointer, API address lists APIs name lists
The IMPORT DATA DIRECTORY looks like:
+-------------------------+-------------------------+
| RVA to a list of | DATE/TIME |
| pointer to APIs names | | IMPORT DATA DIRECTORY
+-------------------------+-------------------------+ #1
| .DLL address (unused) | RVA to .DLL name |
+-------------------------+-------------------------+
|RVA to API address list |
+-------------------------+
| | |
IMPORT DATA DIRECTORY
| | | #n
| | |
+-------------------------+-------------------------+
| NULL | NULL | NULL IMPORT DATA
| | | DIRECTORY to say
+-------------------------+-------------------------+ it's the end
| NULL | NULL |
+-------------------------+-------------------------+
| NULL |
+-------------------------+
- RVA to a list of
pointer to APIs names : This RVA point to a list of others pointers which point to
API NAMEs imported from the .DLL
- DATE/TIME :
- .DLL address (unused) : In win9X this field contains the address where is
load the .DLL file but not under win NT,2000,XP).
Please don't use this value
- RVA to .DLL name : This RVA point to the name of the .DLL file
(library)
- RVA to API address list : This RVA point to the list of API address (the
loader write them...)
Ok let's see the IMPORT section of our hello.exe file:
View of IMPORT section BEFORE loading hello.exe
Physical
offset 0 1 2 3 4 5 6 7 8 9 A B C D E F
00000800 58 30 00 00 00 00 00 00 00 00 00 00 3C 30 00 00 ............<0..
00000810 60 30 00 00 68 30 00 00 00 00 00 00 00 00 00 00 ................
00000820 48 30 00 00 70 30 00 00 00 00 00 00 00 00 00 00 ................
00000830 00 00 00 00 00 00 00 00 00 00 00 00 75 73 65 72 ............user
00000840 33 32 2E 64 6C 6C 00 00 6B 65 72 6E 65 6C 33 32 32.dll..kernel32
00000850 2E 64 6C 6C 00 00 53 04 78 30 00 00 00 00 00 00 .dll............
00000860 78 30 00 00 00 00 00 00 86 30 00 00 00 00 00 00 x0..............
00000870 86 30 00 00 00 00 00 00 00 00 4D 65 73 73 61 67
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -