首先,我创build一个名为SimpleDll.dll
的简单dll,它的头文件:
// SimpleDll.h #ifdef MYLIBAPI #else #define MYLIBAPI __declspec(dllimport) #endif MYLIBAPI int Add(int a. int b);
其源代码:
// SimpleDll.c #include <windows.h> #define MYLIBAPI __declspec(dllexport) #include "SimpleDll.h" int Add(int a, int b) { return a + b; }
然后我在另一个项目中调用它,它工作正常:
// TestSimpleDll.c #include "stdafx.h" #include <windows.h> #include "SimpleDll.h" #pragma comment(lib, "SimpleDll.lib") int _tmain(int argc, _TCHAR* argv[]) { printf("%d", Add(10, 30)); // Give the expected result 40 return 0; }
但是,当我调用GetProcAddress
来获取它的地址时,它不起作用!
// TestSimpleDll2.c #include "stdafx.h" #include <windows.h> #include "SimpleDll.h" #pragma comment(lib, "SimpleDll.lib") int _tmain(int argc, _TCHAR* argv[]) { printf("%d", Add(10, 30)); // Give the expected result 40 HMODULE hModule = GetModuleHandleA("SimpleDll.dll"); // hModule is found PROC add_proc = GetProcAddress(hModule, "Add"); // but Add is not found ! // add_proc is NULL! return 0; }
谢谢你的帮助。 (PS:我在Windows7上使用VS2010)
更新:
这就是依赖walker为SimpleDll.dll
文件显示的SimpleDll.dll
:
如果要为GetProcAddress导出名称,应该使用.def文件。 否则,你将不得不处理c + +名称和符号装饰。
您可以通过将函数声明为extern "C"
来避免重叠,但避免装饰的唯一方法是使用.DEF文件。
还有一件事 – 在Dependency Walker中 – 使用F10在装饰名和未装饰名之间切换。
依赖Walker是一个很好的解决DLL问题的工具。
我假设你正在编译DLL作为C代码。 否则,C ++将执行名称修改,这将导致问题。
为了避免名称修改,只需将输出定义包装在extern“C”中。
extern "C" { MYLIBAPI int Add(int a. int b); }