|
|
请大家注意!这种方法只能应用于输出为C格式的__stdcall调用方式!$ j9 g9 ]; M" I0 {3 o# O2 K) d
0 @( p$ w3 E( ^' }( G
1. 使用VC++的工具DUMPBIN将DLL中的导出函数表导出到一定义(.DEF)文件* A: g1 }$ C4 Q, x* L+ V( ]+ N" D
EXAMPLE:% g" t+ Q5 A! e1 A# w
DUMPBIN VideoDeCoder.dll /EXPROTS /OUT:VideoDeCoder.def
" l4 S6 ]- g+ m# T, p* n& |+ d
$ `' }. c0 b" q- A& T* `5 M! _2. 将导出的.DEF文件整理为一符合.DEF个数的函数导出文件
) g, K' L$ i e- |9 I1 k: u EXAMPLE:+ f3 g+ ?0 x. U8 o5 c& [! q" y
VideoDeCoder.DEF 文件内容如下
0 ]; Q$ u3 ^, D2 Z " i2 I% K' ^- |1 W2 [# D! ~ }" i1 @
Dump of file VideoDeCoder.dll
1 M2 S7 x. C; S, S; ^; X % J5 C+ m" ]* ~5 e `: L
File Type: DLL
) t/ k6 v" ]. c; O- q$ A% f
; x% F8 O, j/ F- T8 U5 {7 [ Section contains the following exports for VideoDeCoder.dll $ G2 a& K5 k6 \( ]) z/ u [
6 E) h" B% @- a- b# X- `6 y 0 characteristics 0 }7 e- Q( B8 h1 z1 f, K+ T A6 t0 ?0 W
3D49E48F time date stamp Fri Aug 02 09:46:55 2002
3 P, @ ]& @3 p: o5 Z 0.00 version
1 z ?7 N' B/ J9 d8 [; B3 o 1 ordinal base
! ~) h ^. |2 C" C* _' e 11 number of functions
* d. M) H$ T; e( C6 _ 11 number of names % u% z" c1 x& d9 J8 K3 g
, Y1 b9 Y0 t8 t( J7 o* p ordinal hint RVA name 1 j- W6 A3 V/ k' A ?1 Y. |( N
' { V2 \$ t {+ Z# p7 I; Y 1 0 00010F60 _TM_ClearDecoderBuff@4 ' ~9 {% j/ Q8 x5 L2 j: o1 [
2 1 00010E80 _TM_CloseDecoder@4 * ^" N6 K6 F( q" K4 ]2 b; V3 b( @" {
3 2 00010F00 _TM_DecodePicture@4
* p0 j; }+ H* j4 U1 O 4 3 00010ED0 _TM_DecodePictureHeader@4 - n5 Q# I) I8 A( z
5 4 00010FD0 _TM_GetFileEnd@4
+ q8 H6 B" [; `/ v9 T$ x" b5 I 6 5 00011030 _TM_GetUValue@4
1 x0 u ^( a. u; U8 l 7 6 00011060 _TM_GetVValue@4 5 g/ b0 S1 W8 D. K0 l j- p" G
8 7 00011000 _TM_GetYValue@4
/ `8 X1 g6 U/ U- ^) J7 ]; L 9 8 00010E10 _TM_OpenDecoder@8
) p3 ^! H7 ]; n7 E; I 10 9 00010F30 _TM_ReturnType@4
0 `" [4 _6 W& f" h3 h 11 A 00010F90 _TM_SetFileEnd@8
0 V, I2 t2 r; ~1 u
6 w3 S! A) n7 z7 V+ [4 r Summary 1 k/ a* c, Q1 I% N; U/ {' `/ m. y
0 S i5 @9 b3 C6 |4 F c
2000 .data , ]7 O5 d- \: d: h% F% c/ [
1000 .rdata 1 C8 ?. |1 Y# y" D6 \3 f& n9 o+ m
1000 .reloc
1 p8 I4 `7 s$ N$ z8 M 15000 .text * |: u1 ]6 `8 G) @
按照以下方法整理:9 x W2 X, o5 I& E
1>添加LIB说明
. W+ T# T8 { z0 h* s8 V9 V+ S LIBRARY "VideoDeCoder" ;"xx"为DLL名称
' ?! l7 V0 A: _% L9 a DESCRIPTION "VideoDeCoder library" ( w O, s' E8 Q
2>去掉导出函数说明端以外的内容,在LIB说明下添加 "EXPROTS" 说明导出函数
$ W/ b; M) B8 P r, O R' S LIBRARY "VideoDeCoder"
5 h( s' t' e; _ x; _ DESCRIPTION "VideoDeCoder library"- f2 S1 w. b" ]0 ?
EXPORTS4 ]3 C) s. x2 r3 L' P1 d
ordinal hint RVA name
( K C7 o" _. c* w( x, s; v8 s3 V0 G ( K* X$ p# e5 E+ v2 ?: ~: S9 a9 \
1 0 00010F60 _TM_ClearDecoderBuff@4 3 C* C o. X0 C- [# O6 M
2 1 00010E80 _TM_CloseDecoder@4
: m- p9 ^: n2 U$ c 3 2 00010F00 _TM_DecodePicture@ , v' S" }' X7 ^
4 3 00010ED0 _TM_DecodePictureH
' m% ? d( x" l+ X! I% \6 a 5 4 00010FD0 _TM_GetFileEnd@4 6 O! | \1 x/ b4 W2 m7 u- @" U
6 5 00011030 _TM_GetUValue@4 9 e+ G9 t. R' B! I, G
7 6 00011060 _TM_GetVValue@4 ) q1 \! K. ?" m) i* u) p
8 7 00011000 _TM_GetYValue@4 - F2 d3 D/ [" _$ \2 n% N& O& g" g/ Z
9 8 00010E10 _TM_OpenDecoder@8 9 L- K/ s8 m/ z
10 9 00010F30 _TM_ReturnType@4
& Z6 S* W+ Y8 c, i% p8 ~* Y. s 11 A 00010F90 _TM_SetFileEnd@8 % o4 G+ T4 A. V
3>将所有的函数放至行首,去掉 "hint" 和 "RVA" 数据,留下函数的序号 "ordinal" ,在序号前加上 "@" 符号
2 z7 Y0 X0 J2 b/ i- r r. w8 ] 形成 "_导出函数名@参数字节和 @序号" 此种格式(__stdcall 方式调用导出的函数符号是 "函数名称@参数字节和").
7 i* w. H" T8 |) p! R) J 最后形成.DEF文件如下:
9 {$ S6 d' w- N' s) b LIBRARY "VideoDeCoder"" Q4 q; Y9 K4 q9 y
DESCRIPTION "VideoDeCoder library"/ r7 \; n& G$ Y8 A9 s
EXPORTS2 P( G9 I3 b7 T$ c
" r) ~ [" x9 R
TM_ClearDecoderBuff@4 @1
/ V4 R X; _8 |; T, q9 X TM_CloseDecoder@4 @2 * \, S" ]+ Y5 Q9 H3 e& X& L" }
TM_DecodePicture@4 @3
1 b# U: R, B4 _( J TM_DecodePictureHeader@4 @4
% R/ U' ?) f$ [6 G } TM_GetFileEnd@4 @5
9 Z5 f& A8 D1 Z- x4 V& ^ TM_GetUValue@4 @6
1 j! C% ^# Y" C' {: k; o TM_GetVValue@4 @7
: q3 e9 D+ R2 @8 c1 x TM_GetYValue@4 @8
/ t# h( V+ c V3 ?% Y TM_OpenDecoder@8 @9
! g) i5 l5 R F5 v# q- l1 u TM_ReturnType@4 @10 , j, X0 W0 Z2 S
TM_SetFileEnd@8 @11
/ p3 x- R5 q# T! C/ a8 h1 I8 p3. 使用VC++的LIB工具,带/DEF:(.def文件名) /MACHINE:IX86(80X86机器),就输出符合VC++格式的的LIB文件了.8 [+ `, l4 V9 T
EXAMPLE:: l9 G! r E& S. D. R" D& _
LIB /DEF:VideoDeCoder.def /MACHINE:IX86
- b2 T* _' @* Q4. 接时带上LIB文件链接;注意的是当有些动态库DUMPBIN的只有函数名,无"@nn"的参数格式,如C++Builder写的DLL,输出就只有函数名符号,链接时就会报错:
- x" v, T: S+ a6 j! t error LNK2002:unresolved external symbol "functionname@nn"
/ p: v) u) h: k( ]: \0 _提示程序中引入的函数符号无法识别,这时只要将DEF文件中相应的函数名称改为functionname@nn方式,重新建立
0 a& |9 i5 b) zLIB,重新链接即可.- r; L" F% Z2 c: x) y
Q' G4 O: X3 f% [2 ~
这样就制作成功了符合VC调用方式的LIB了!
[; J8 ~+ y! z参考:MSDN20002 v4 O0 {' _! U. C- L7 p
要值得一说的是!BORLAND C++BUILDER有一个很好的工具IMPDEF可以直接将DLL中的函数输出到.DEF文件中,只要做一点点修改就可以成为符合VC的DEF文件!
% [1 R! g1 y) K0 pIMPDEF xxx.def xxx.dll8 K& b3 ?7 o" ]( {- L+ ~3 N/ E# K
这种方法只能应用于输出为C格式的__stdcall调用方式经过我的论证有些错误!我利用Borland C++和VC++做论证,发现:
/ ^1 m$ h h7 D1 V而在C++BUILDER中!1 p. j2 z- b0 H, r/ D
__cdecl的函数输出前会带一"_"
$ ^" I' }/ F7 c0 ___stdcall无特征,只输出函数名0 E, r, g) T# ~) g6 w
__fastcall函数输出前带一"@"6 M: `( \* D/ }
都无"@nn"后缀格式!
, Q/ y7 c+ W6 k; z4 c在VC中!0 j( ~, P( R; X, M6 I* S1 m4 d
__cdecl无特征,只输出函数名
. p- r& [8 e8 m__stdcall的函数输出前会带一"_"后缀带"@nn"
& X2 X% j8 Y" U* ~4 m" ~8 ~5 W__fastcall函数输出前带一"@"后缀带"@nn
$ ?: B. Y5 U$ |# `& `% s只要将BC的DEF文件中函数申明格式转换为VC识别的格式就可以利用LIB工具生成LIB;要使用C分格输出(extern "C")才是必须的!而且别忘了在DEF文件中的函数申明不要带“_”啊!:)不然会出现error LNK2001的链接错误! |
|