2012-01-25 64 views
0

我有MYDLL.DLL,它的功能定義如下關於GetProcAddress的

void pascal Myfunction(BOOL); 

當我試圖使用該功能在另一個項目中,我無法用GetProcAddress()得到函數的地址。這裏是我的代碼:

void callMyDll() 
{ 
HINSTANCE hDll; 

hDll=LoadLibrary(_T("MyDll.dll"); 

if(hDll!=NULL) 
{ 
    cout<<"\n DLL Loaded \n"; 
} 
else 
    cout<<"\n DLL Not loaded\n" 

typedef void (__stdcall *MyFunction)(bool) 

Myfunction mf1 = (MyFunction) GetProcAddress(hDll, "MyFunction"); 

if (mf1!=NULL) 
    cout<<"\n Function Loaded Successfully \n"; 
else 
    cout<<"\n Function not loaded \n"; 

FreeLibrary(hDll); 
} 

我收到輸出:

DLL Loaded 
Function not loaded 

但是,當我與已知的DLL像要將glut32.dll,其職能是工作的罰款嘗試。

我認爲這可能是問題,像

其功能
void pascal MyFunction(BOOL); 

任何人可以幫助我在這方面?

+0

函數是否已導出? –

+0

我已經將這個頭文件包含爲 – srinivasporam

+0

你記得導出函數嗎? –

回答

0

爲什麼使用pascal調用約定?也許這會改變符號的名稱,如果是這樣的話,您可能需要考慮這一點。

+0

'pascal'是一個16位調用約定,它被定義爲32位的__stdcall。 –

2

您需要使用extern "C"防止名字改編,確保功能輸出:

extern "C" __declspec(dllexport) void Myfunction(BOOL); 

要查看您的DLL出口,你可以使用dumpbin.exe實用程序,它隨Visual Studio的:

dumpbin.exe /EXPORTS MyDll.dll 

這將列出所有導出符號的名稱。

除此之外沒有任何指定以下編譯器開關:

Gz __stdcall calling convention: "Myfunction" would be exported as [email protected] 
Gr __fastcall caling convention: "Myfunction" would be exported as @[email protected] 

注:我覺得最後一個符號是依賴於編譯器的版本,但仍然是不只是「MyFunction的」。

+1

該函數被聲明爲'pascal',它與x86上的'__stdcall'相同,因此無論編譯器選項是什麼,__declspec(dllexport)'都會被修飾。因此,除非使用.def文件,否則它將是'_Myfunction @ 4'。 –

+0

@DavidHeffernan,謝謝你指出。我在答案中省略了「pascal」調用約定,但這對OP來說可能是必需的。 – hmjd

1

DLL導出過程受制於名稱的修飾和裝飾。長期過時的16位pascal調用約定相當於32位平臺上的stdcall

首先,您應該使用extern "C"來指定C鏈接並禁用名稱修改。

但是,您的功能仍將受到name decoration的約束。如果您用__declspec(dllexport)導出它,那麼它實際上將以名稱[email protected]導出。如果你想通過它的真實名稱導出它,那麼你需要使用一個.def文件。

但是,仍然存在的可能性仍然是你根本沒有從DLL中導出函數。使用Dependency Walker來檢查它是否被導出,如果是,按什麼名稱。

0

該符號將被裝飾,所以它永遠不會被稱爲MyFunction,更可能是[email protected]。你可以使用類似dumpbin的東西來快速檢查。

你可以閱讀更多有關mangling here的信息,如果你想避免重疊,你需要使用def文件來指定符號名稱(或序號)。

+0

雖然在原文中還不清楚,但看起來'extern「C」'正在使用,這將防止函數名稱被破壞(前提是調用約定沒有被覆蓋),但我要求輸出函數聲明只是爲了確保。 –

+0

@AdamMaras:它仍然會在Windows上至少得到一個約定前綴(參見我的鏈接),'extern「C」'只是說它必須對C風格的裝飾,但他反正使用C,其冗餘 – Necrolis

+0

非常感謝可以加載的功能..這很好 – srinivasporam