使用DLL進行不同語言之間的呼叫

2021-04-20 03:18:52 字數 4777 閱讀 5734

複製內容到剪貼簿

**:extern "c" __declspec(dllexport) int  max(int x,int y)

__declspec(dllexport) int __stdcall min(int x,int y)

/*這和前面的例子重複了,主要用於呼叫的例子

*/dllexport double __stdcall max_d(double x,double y)

接下來是使用結構體的,由於結構體會對成員進行對齊,

所以在呼叫的時候需要注意和這裡的結構體有相同的記憶體布局

複製內容到剪貼簿

**:#include

struct teststruct

;dllexport int __stdcall usestruct(teststruct* p)

/*這是修改了記憶體對齊的結構體使用,主要在呼叫的時候有區別*/

#pragma pack(push)

#pragma pack( 1 )

struct teststruct2

;#pragma pack(pop)

dllexport int __stdcall usestruct2(teststruct2* p)

這是使用**函式的例子,這裡想成功呼叫主要還是要看如何呼叫.

複製內容到剪貼簿

**:dllexport int __stdcall usercallbackfunc( const char* lp, int (__stdcall *p)(const char*) )

def檔案內容如下

exports

maxswap

max_d

usestruct

usestruct2

usercallbackfunc

這裡的def檔案不是必須的,如果不使用def檔案編譯,則dll中的一些函式名前面會被加上_後面加上引數大小

?min@@yannn@z ?min@@yghhh@z max _max_d@16 _usestruct2@4 _usestruct@4 _usercallbackfunc@8 swap

當然如果只是c使用的話不使用def檔案也是可以的,但要是其他語言的話就有一些不方便了也得使用_max_d@16

這樣的函式名字,有些不美觀.在這裡增加def檔案也就是改名的意思

編譯方法如下

cl /c dlltest.cpp

link /dll /def:dlltest.def dlltest.obj

使用了def檔案後dll中所匯出的函式如下

?min@@yannn@z ?min@@yghhh@z max max_d usestruct2 usestruct usercallbackfunc swap

除去過載的兩個函式,凡是使用extern "c"的函式都可以正常現實

c/c++的使用方法

分別使用.c和.cpp的副檔名編譯,就是c的呼叫方法和c++的呼叫方法了

複製內容到剪貼簿

**:#ifdef __cplusplus

extern "c" __declspec(dllimport) int  max(int x,int y);

int __stdcall min(int x,int y);

double min(double x,double y);

#else

__declspec(dllimport) int max(int x,int y);

#endif

#ifdef __cplusplus

#    define dllimport extern "c" __declspec(dllimport)

#else

#    define dllimport __declspec(dllimport)

#endif

dllimport int swap(int* x,int* y);

dllimport double __stdcall max_d(double x,double y);

#include

typedef struct __teststruct

teststruct;

dllimport int __stdcall usestruct(teststruct* p);

#pragma pack(push)

#pragma pack( 1 )

typedef struct __teststruct2

teststruct2;

#pragma pack(pop)

dllimport int __stdcall usestruct2(teststruct2* p);

dllimport int __stdcall usercallbackfunc( const char* lp, int (__stdcall *p)(const char*) );

#include

#pragma comment(lib,"dlltest.lib")

#include

int __stdcall callbackfunc(const char*lp)

int main()

;

delphi的使用方法

複製內容到剪貼簿

**:vb6的使用方法

由於vb6只能使用__stdcall方式的函式,所以只有部分函式能被vb6所呼叫。

複製內容到剪貼簿

**:public declare sub copymemory lib "kernel32" alias "rtlmovememory" (destination as any, source as any, byval length as long)

public declare function lstrlen lib "kernel32" alias "lstrlena" (byval lpstring as long) as long

public type teststruct

a as byte

b as long

c as double

sz as string * 5

end type

public type temp

sz as string * 5

end type

public declare function max_d lib "dlltest" (byval a as double, byval b as double) as double

public declare function min lib "dlltest" alias "?min@@yghhh@z" (byval a as long, byval b as long) as long

public declare function usestruct lib "dlltest" (byref a as teststruct) as long

public declare function usestruct2 lib "dlltest" (byref a as any) as long

public declare function usercallbackfunc lib "dlltest" (byval s as string, byval f as long) as long

function callback(byval lp as long) as long

dim l as long

l = lstrlen(lp)

dim s as string

s = string$(l + 1, vbnullchar)

copymemory s, lp, l

msgbox s & " , " & str$(l)

debug.print "callback", s

callback = 3

end function

sub main()

debug.print max_d(4, 5), min(4, 6)

dim a as teststruct

debug.print usestruct(a)

debug.print chr(a.a), a.b, a.c, a.sz

dim buf(18) as byte

debug.print "----------------"

debug.print usestruct2(buf(0))

dim t as byte

copymemory t, buf(0), 1

dim l as long

copymemory l, buf(1), 4

dim d as double

copymemory d, buf(5), 8

dim s as temp

copymemory s, buf(13), 5

debug.print chr(t), l, d, s.sz

debug.print usercallbackfunc("_測試asdasd中文sdfasdf", addressof callback)

end sub

vb版本需要注意的是lstrlen 的宣告 引數不是string而是long型別,這是因為如果是string的話vb會對引數進行改造,將字串指標轉化為string型別,而我這裡不需要改變,就需要乙個原始的long型別的指標.所以就更改了api的函式宣告.以適應我的需求。

C語言之不同的單詞

problem description 給出乙個英文單詞的列表,計算有多少不同的單詞在列表中。input 本題有多組輸入資料,你必須處理到eof為止 每組資料的第一行有乙個整數n,1 n 1000.下面的n行每行乙個單詞,每個單詞的長度不超過20。單詞大小寫忽略。output 每組資料輸出乙個整數,...

語言之間的轉換(思想)

語言的轉換就如同機器翻譯一樣,如果想從風格上做翻譯,機器得理解這個程式。不過,感覺理解程式可能比理解自然語言還是要容易一些的,畢竟詞法和語法分析是死的,可能的演算法和資料結構也非常有限。我覺得,可能的思路 首先當然是需要把源語言的 進行預處理,比如程式設計ast之類的 第二步就是一些高階的模式識別工...

使用VarDumper進行優雅的PHP除錯

相信很多php開發者在寫 的時候都會經常用到var dump 這個函式,很多人都會直接用類似die var dump var 來檢視乙個變數或者乙個例項到底是長什麼樣的,稍微有一些人可能還直接封裝過 比如直接叫乙個vdd 等,以便於自己在除錯自己的 的時候使用。這種方式一直陪伴著我走過了這麼久的程式...