1、前言:为什么要这么做
7 i/ ?3 y9 p5 E, A" e& w; {% U3 d, i很多时候,我们发现一个PE(EXE或DLL)中非常有用且功能独立的函数(call xxxxxxxx),并且已经知道了这个函数的各个入口参数的类型和具体含义,我们想在其他的软件中使用这个函数。于是,我想到了将这个PE中的函数改成一个导出函数,这样,我们就可以在任何软件中通过“LoadLibrary("ThisPE.EXE")”等API来使用这个函数了。
1 q. e" x& X V- t# S. D8 s+ g) N9 i5 O; V' \
在汉化中的应用是可以直接调用游戏中的解包,压包函数来解包,压包,以及访问游戏中的文本显示函数等等。。。
! ^2 i4 S2 f" C* V$ ] A8 Y1 [$ y" U2 g; K8 k, ~7 d7 m3 x
2、技术基础:已经了解PE结构 # Z7 G+ h- K/ L' m6 r+ y' [; |
$ N8 W% P/ @9 i' v8 w# o2 L3 J- m6 p
3、分类:
. U0 S( f: J, G! n2 Z) N(1)有导出表的DLL和EXE文件--非常简单
5 A$ q1 A8 t! m+ w1 Z对于这类PE文件,要简单的多,因为只要修改一下PE中的Export,增加上一个导出函数,并把这个导出函数的入口指向我们要导出的call的调用地址(RVA格式)就可以了。甚至可以更简单的处理:找个不用的导出函数,改一下入口就可以了。 & p; s# }* P( O0 Q- v+ s
(2)没有导出表的EXE文件--稍微复杂
( P7 b. n! s$ t( b' y6 k因为大部分EXE文件没有导出表,所以我们必须要给它增加一个导出表。其实也很简单,给EXE增加一个节,并在这个节中按照导出表的格式构造一个导出函数,并将这个函数入口指向我们要导出的call的调用地址的RVA,并在PE头中指出其位置和大小。 9 l4 [# F- i0 t/ A* i
& w" c+ F2 G! S, m' g4、举例说明:
6 L1 }) s$ q4 p3 e. Ctest.exe:ImageBase=0x00400000
/ A( V6 f1 @; R7 n: y) l发现test.exe 的 0x00408050 处为call 0x0040A012 的 0x0040A012是我们要导出的函数,我们将它导出为MyFunction函数。
4 C4 |) w% D0 y& p, \6 ?# H2 \3 `+ p4 K! X$ n/ W
(1)给test.exe增加一个节:RVA=0x28000,size=0x1000 : J, C/ N- F# q1 K
(2)构造导出表: % c; r3 U- J" q v. G1 e
My_Export_Table dd 0 ;Characteristics
& s* ^( g& V: t/ J* l+ }+ PMy_TimeDateStamp dd 0 ;TimeDateStamp / U' { {! l. i4 d
dw 0 ;MajorVersion
5 [5 e9 _8 J* z! }8 @dw 0 ;MinorVersion ' j9 I2 j8 W" d, n- N+ q9 z1 R
My_nName dd My_DLL_nName-ImageBase ;nName / j+ m4 `) N' l5 G
dd 1 ;nBase - E1 j1 |) k$ q2 a: F
dd 1 ;NumberOfFunctions # G. f2 W! [$ K8 D! w
dd 1 ;NumberOfNames 5 A" _- T! L5 Q2 w7 w8 y U
My_AddressOfFunctions dd 0x0040A012-ImageBase ;AddressOfFunctions
0 p5 R6 G7 S1 C& wMy_AddressOfNames dd My_Fun_Name-ImageBase ;AddressOfNames 0 @& Q) H+ C6 v8 Q* d+ U, P
My_AddressOfNameOrdinals dd 0 ;AddressOfNameOrdinals
Z3 t4 ^3 o" V8 {5 g' f--------------------------------------------------------------------- % V7 k: C) G3 o& b9 F* H5 `$ E6 f4 k
My_Fun_Name db 'MyFunction',0
. v; K0 N v! f$ K9 y$ \9 TMy_DLL_nName db 'test.exe',0 ) R. r a7 q- C6 A
$ \7 _/ e* o+ P/ n) R4 x: ]
(3)LoadPe修改PE头,将导出表地址填入0x28000,大小填入0x1000,保存。
: [3 W, N, P }' ^) O
( F+ E& f/ g) T" z5 e# B& d7 H! @Spirng.W/2005.3.14 ' T( g' |# W* c- q: T* J3 L* I7 t
- t" N3 H f# _+ \: S% J7 ~
) R0 R ]& J1 w-------------------------------------------------------------------------------- |