|
|
请大家注意!这种方法只能应用于输出为C格式的__stdcall调用方式!
7 v7 b/ c, c @. u, `* s, i7 I9 [; i( U5 }7 i! d4 z6 Q7 [
1. 使用VC++的工具DUMPBIN将DLL中的导出函数表导出到一定义(.DEF)文件
3 r0 l" l8 O. v h1 {' d5 s EXAMPLE:
2 m" b( i( K8 S) y DUMPBIN VideoDeCoder.dll /EXPROTS /OUT:VideoDeCoder.def
9 x( {3 y6 z' y- u) `" r ' d* @% I1 ?, ?% U
2. 将导出的.DEF文件整理为一符合.DEF个数的函数导出文件/ ?) l) m" W; `
EXAMPLE:
5 v$ T6 k0 p/ v3 l8 v VideoDeCoder.DEF 文件内容如下
& l1 c3 @/ s- j- Q/ ` ( {) @! K" y6 \% W! ~
Dump of file VideoDeCoder.dll
. m! w0 O) c& d, {! L- G $ \, s$ P7 d0 x1 Y
File Type: DLL
+ y% A. e6 A! e* ^: w+ \* Z % J K' Z0 {0 O+ c; z2 q3 p
Section contains the following exports for VideoDeCoder.dll ) Z/ X* Q% n0 {- \5 C
5 C& X) Z+ K5 z8 e 0 characteristics
$ J4 k. t$ b! c: N: B. B 3D49E48F time date stamp Fri Aug 02 09:46:55 2002 # z. g- B8 z; z- h0 I9 b# `
0.00 version
0 N$ q) T3 J4 ]+ ` 1 ordinal base
z, l; X* S8 B9 P% y 11 number of functions
' M' K" d! S) l) M 11 number of names
$ c$ T) D6 i, O. r7 A ( r- b3 F8 [9 W5 R! c* j P9 E
ordinal hint RVA name 9 H+ e, J0 c" }2 r1 S) \
8 s3 N- b+ E4 D
1 0 00010F60 _TM_ClearDecoderBuff@4
" @4 W- w4 y4 l# b! ?0 R, c 2 1 00010E80 _TM_CloseDecoder@4
% S) r2 P7 y$ M' Z& F9 H 3 2 00010F00 _TM_DecodePicture@4 4 B, |) K& S& H" B& }
4 3 00010ED0 _TM_DecodePictureHeader@4
/ A& d0 w3 ^) V2 e, b% S* u 5 4 00010FD0 _TM_GetFileEnd@4 * o( M1 [+ u. G8 Q, _% E4 O
6 5 00011030 _TM_GetUValue@4
1 r' V5 t/ B$ V$ o7 T/ R 7 6 00011060 _TM_GetVValue@4
+ i4 v* B1 B0 Q: h* e& r 8 7 00011000 _TM_GetYValue@4 2 h* G+ d+ n- e9 E2 p
9 8 00010E10 _TM_OpenDecoder@8
8 {, B; Q: }4 J. a3 X 10 9 00010F30 _TM_ReturnType@4 + v* A# j/ G8 [* j! T
11 A 00010F90 _TM_SetFileEnd@8 ; c9 ^) A9 d4 n4 _ t
9 D" l$ r8 j; @/ T Summary
/ [2 G! q. g& U k 0 T4 U5 q4 {' M/ g* v$ K) n
2000 .data $ A$ }8 U$ u8 t! _4 Z0 N R; \
1000 .rdata
* J7 b) C! F4 Q6 }. ~ 1000 .reloc & q$ K. Y5 Y% |; W6 H7 _2 T' V+ G0 V
15000 .text
+ `$ E; k" G) k, d* u" F; C2 } 按照以下方法整理:
* E! d1 I. V3 B* p" R2 R 1>添加LIB说明
; P7 ?# O) ^6 S+ U* {- U, j$ `$ Y# n LIBRARY "VideoDeCoder" ;"xx"为DLL名称3 T2 {0 t# |7 Y! l1 B- o; K% |
DESCRIPTION "VideoDeCoder library" 9 i T& ^) N# `8 S
2>去掉导出函数说明端以外的内容,在LIB说明下添加 "EXPROTS" 说明导出函数& h, p! V: u) G4 @4 C
LIBRARY "VideoDeCoder"/ x' c+ _5 h) W$ M6 I7 o5 @% Q5 A j) a
DESCRIPTION "VideoDeCoder library"
/ p! ?: [( j* K EXPORTS
. i6 ^0 H6 o) b7 ~ ordinal hint RVA name : R+ B) f" q( j; i% P) O
2 D/ T5 z- R' v
1 0 00010F60 _TM_ClearDecoderBuff@4
4 F. J8 E" B( d6 @6 T9 N 2 1 00010E80 _TM_CloseDecoder@4
: g+ r: T' ~6 w) R: [ 3 2 00010F00 _TM_DecodePicture@ * D& o1 k: H" N# g
4 3 00010ED0 _TM_DecodePictureH - L) b7 d* ^7 D9 z$ q" C" D
5 4 00010FD0 _TM_GetFileEnd@4 & o* C; S9 e, f6 ]# C0 I
6 5 00011030 _TM_GetUValue@4
$ F( w% K0 E; L% @! V6 y* ` 7 6 00011060 _TM_GetVValue@4 ) _) W7 ?% q4 F6 Z- U
8 7 00011000 _TM_GetYValue@4 $ [' j: J* o% y
9 8 00010E10 _TM_OpenDecoder@8 , X3 ?: Y/ R$ ^5 H0 R9 Q
10 9 00010F30 _TM_ReturnType@4
& ` p* j W9 y% X7 R( w- |9 F 11 A 00010F90 _TM_SetFileEnd@8
" M7 N- q& |+ F 3>将所有的函数放至行首,去掉 "hint" 和 "RVA" 数据,留下函数的序号 "ordinal" ,在序号前加上 "@" 符号, E7 b! j/ G+ e9 q( @6 \* S& @* c
形成 "_导出函数名@参数字节和 @序号" 此种格式(__stdcall 方式调用导出的函数符号是 "函数名称@参数字节和").
8 d/ H0 n& y# u$ v* q R- o 最后形成.DEF文件如下:
. z4 e/ t% n( ~( _: Y LIBRARY "VideoDeCoder" x3 O% Q. f5 n( f6 W T
DESCRIPTION "VideoDeCoder library") ^& S7 s* }+ w3 {& D
EXPORTS
+ o5 Y$ L9 T% E5 e 0 M) X- l/ l! R$ `
TM_ClearDecoderBuff@4 @1 . t# y1 `* k$ f6 u
TM_CloseDecoder@4 @2 % E% f0 V: d$ H% y
TM_DecodePicture@4 @3 1 X5 L4 P& a6 ^' p
TM_DecodePictureHeader@4 @4
0 V) r2 L5 r6 w% A( C ] TM_GetFileEnd@4 @5
T1 |) _* b- R' z- S7 |; O& o$ [ TM_GetUValue@4 @6
2 f" q) X. c; `3 i- p" ~! j3 H TM_GetVValue@4 @7
5 J$ s$ \3 D/ K+ n( G TM_GetYValue@4 @8 s+ N! b. T% o7 |& E z
TM_OpenDecoder@8 @9 9 x1 Y9 R/ i! |
TM_ReturnType@4 @10
3 L5 e1 @% f; B. X" j" F+ o TM_SetFileEnd@8 @11
5 z' b9 w0 L [. G4 Y! V2 e1 P3. 使用VC++的LIB工具,带/DEF:(.def文件名) /MACHINE:IX86(80X86机器),就输出符合VC++格式的的LIB文件了.
# \8 i5 e! k( [9 ?: H EXAMPLE:
( O8 h% u/ j- B7 Q0 E/ s2 s LIB /DEF:VideoDeCoder.def /MACHINE:IX865 P( j: |7 r* Q2 ]
4. 接时带上LIB文件链接;注意的是当有些动态库DUMPBIN的只有函数名,无"@nn"的参数格式,如C++Builder写的DLL,输出就只有函数名符号,链接时就会报错:
& q7 k3 v' a U error LNK2002:unresolved external symbol "functionname@nn"( {' z0 y2 {: B
提示程序中引入的函数符号无法识别,这时只要将DEF文件中相应的函数名称改为functionname@nn方式,重新建立. f/ T8 E1 B% i
LIB,重新链接即可.
+ o8 o" ]) Y: c. w2 z
9 O! b2 u2 I( H* R& U- O) F' x d* u这样就制作成功了符合VC调用方式的LIB了!* }1 Z4 d& ?, f1 r+ Y' S7 j
参考:MSDN2000
) `- ~: Q1 G7 F* g$ G要值得一说的是!BORLAND C++BUILDER有一个很好的工具IMPDEF可以直接将DLL中的函数输出到.DEF文件中,只要做一点点修改就可以成为符合VC的DEF文件!9 u5 i* m1 S( Q1 P+ y/ T$ E. ?
IMPDEF xxx.def xxx.dll, u* ]1 ~- v' W$ |1 L) x/ j1 |" X
这种方法只能应用于输出为C格式的__stdcall调用方式经过我的论证有些错误!我利用Borland C++和VC++做论证,发现:2 g' _4 X( m5 S
而在C++BUILDER中!$ ^8 d C s+ U& _. y& O$ y
__cdecl的函数输出前会带一"_"0 e" |" r: N! n) ]! }- g
__stdcall无特征,只输出函数名
; ~% B8 r5 s5 q7 D__fastcall函数输出前带一"@"
) n$ K/ a. r* U) J都无"@nn"后缀格式!5 c0 p) K7 G' Z8 R" R% B
在VC中!
% c9 W" A' J* f# U8 B' i+ Z; x__cdecl无特征,只输出函数名
+ x' l9 m: x6 C4 B__stdcall的函数输出前会带一"_"后缀带"@nn"3 _/ ?$ v9 D' V3 S1 r
__fastcall函数输出前带一"@"后缀带"@nn
5 _0 D+ g* i3 E- }- g) Z只要将BC的DEF文件中函数申明格式转换为VC识别的格式就可以利用LIB工具生成LIB;要使用C分格输出(extern "C")才是必须的!而且别忘了在DEF文件中的函数申明不要带“_”啊!:)不然会出现error LNK2001的链接错误! |
|