此问题基于以下帖子:https://stackoverflow.com/users/9999861/blackbriar
现在,我遇到了每次我要使用dll时都会出现System.EntryPointNotFoundException
的问题。异常消息说,在我的dll中找不到带有我尝试调用的函数名称的入口点。
这是一个位于.h文件中的示例函数:
#ifdef __cplusplus
extern "C"
{
#endif
__declspec(dllexport) int __stdcall LDL_Init(char* code)
...
#ifdef __cplusplus
}
#endif
我将函数导入C#中,如下所示:
[DllImport("C:\\Path\\To\\Dll\\Example.dll", EntryPoint="LDL_Init", CallingConvention=CallingConvention.StdCall)]
public static extern int LDL_Init( [MarshalAs(UnmanagedType.LPStr)] System.Text.StringBuilder code );
有人知道我在做什么错吗?
下一步尝试:
我用Dependency Walker分析了生成的dll,并确认没有导出任何函数。所以我写了一个包装类。这里是新的代码示例:
在Library.h中:
int LDL_Init(char* code);
在LibraryWrapper.h中:
#pragma once
class __declspec(dllexport) LibraryWrapper
{
public:
static int __cdecl LDL_Init(char* code);
};
在LibraryWrapper.cpp中。
#include "Library.h"
#include "LibraryWrapper.h"
int LibraryWrapper::LDL_Init(char* code){
return LDL_Init(code);
}
在Library.cs中:
[DllImport("C:\\Path\\To\\Dll\\Example.dll")]
public static extern int LDL_Init( [MarshalAs(UnmanagedType.LPStr)] System.Text.StringBuilder code );
可悲的是,我在执行程序时得到了相同的结果:很好的旧System.EntryPointNotFoundException
...
答案 0 :(得分:1)
您可以使用Microsoft DUMPBIN.EXE
工具检查导出:
> dumpbin /EXPORTS Example.dll
Microsoft (R) COFF/PE Dumper Version 14.14.26433.0
Copyright (C) Microsoft Corporation. All rights reserved.
Dump of file Example.dll
File Type: DLL
Section contains the following exports for Example.dll
00000000 characteristics
FFFFFFFF time date stamp
0.00 version
1 ordinal base
2 number of functions
2 number of names
ordinal hint RVA name
2 0 000110C3 LDL_Init = @ILT+190(LDL_Init)
1 1 00011087 foo = @ILT+130(foo)
Summary
1000 .00cfg
1000 .data
1000 .idata
2000 .pdata
3000 .rdata
1000 .reloc
1000 .rsrc
8000 .text
10000 .textbss
编译器需要查看链接器的任何特殊内容,例如__declspec(dllexport)
或#pragma comment(lib, ...)
,否则编译器将看不到它们的任何线索,链接器也不会。对于修改后的头文件,这意味着至少要包含它们一次。
或者,对于模块定义文件(.def
),它需要添加到项目中(或手动添加/DEF filename
命令行参数)。
答案 1 :(得分:0)
如果可能,请使用__cdecl。
__ stdcall将在函数名称后添加@parameter_bytes。
答案 2 :(得分:0)
我通过文件Library.cs中的以下调整“解决了”问题:
[DllImport("C:\\Path\\To\\Dll\\Example.dll", EntryPoint="?LDL_Init@LibraryWrapper@@SAHPEAD@Z")]
public static extern int LDL_Init( [MarshalAs(UnmanagedType.LPStr)] System.Text.StringBuilder code );
字符串EntryPoint基于Dependency Walker从我的dll中提取的函数名称。之后,我遇到了一个问题,即代码的执行停在了行
return LDL_init(code);
在文件LibraryWrapper.cpp中。通过启用“本机代码调试”并在调试时按暂停来发现这一点。
同时,我找到了一个我要控制的设备的生产者提供的.dll。我使用Dependency Walker分析了.dll,并插入了EntryPoints。现在可以了。感谢您的支持。