我正在构建一个c#类库,它调用我们正在使用的供应商提供的第三方DLL。供应商的例子都是vc ++,并且正在运行和运行。
我正在尝试加载其中一个DLL并且它返回IntPtr
0.当我调用Marshal.GetLastWin32Error()
时,我得到193,这是我读过的,意味着我正在尝试加载64位应用程序中的32位DLL。但我一次又一次地检查,我的类库都设置为x86
,我的控制台应用程序调用该类库设置为x86
。
我可以通过同一个供应商(也是32位)成功加载其他DLL文件。
这是我的Native助手类:
class NativeHelper
{
[DllImport("kernel32.dll", EntryPoint = "LoadLibrary", SetLastError = true)]
public static extern IntPtr LoadLibrary(string dllToLoad);
[DllImport("kernel32.dll", EntryPoint = "LoadLibraryEx", SetLastError = true)]
public static extern IntPtr LoadLibraryEx(string dllToLoad, IntPtr hFile, LoadLibraryFlags flags);
[DllImport("kernel32.dll")]
public static extern IntPtr GetProcAddress(IntPtr hModule, string procedureName);
[DllImport("kernel32.dll")]
public static extern bool FreeLibrary(IntPtr hModule);
[System.Flags]
public enum LoadLibraryFlags : uint
{
DONT_RESOLVE_DLL_REFERENCES = 0x00000001,
LOAD_IGNORE_CODE_AUTHZ_LEVEL = 0x00000010,
LOAD_LIBRARY_AS_DATAFILE = 0x00000002,
LOAD_LIBRARY_AS_DATAFILE_EXCLUSIVE = 0x00000040,
LOAD_LIBRARY_AS_IMAGE_RESOURCE = 0x00000020,
LOAD_WITH_ALTERED_SEARCH_PATH = 0x00000008,
LOAD_LIBRARY_SEARCH_DLL_LOAD_DIR = 0x00000100,
LOAD_LIBRARY_SEARCH_SYSTEM32 = 0x00000800,
LOAD_LIBRARY_SEARCH_DEFAULT_DIRS = 0x00001000
}
}
这就是我打电话的方式:
IntPtr pDll = NativeHelper.LoadLibrary(@"dhplay.dll"); // returns 0
if (pDll == IntPtr.Zero)
{
var err = Marshal.GetLastWin32Error().ToString(); // returns 193
Console.WriteLine(err);
}
我在这里缺少什么?如果我正在运行x86
为什么DLL没有加载而其他人没有加载?
修改(其他信息):
IntPtr.Size
是4
dumpbin
返回8664 machine (x64)
- 这意味着它是64位?我检查了其他使用的DLL,它们是8664 machine (x86)
就依赖关系而言,它正在我的机器上运行vc ++应用程序。
答案 0 :(得分:0)
如果有烟,经常会发生火灾。一些dll可能是x64,而你的应用是x32(或相反)。
检入应用IntPtr.Size
。 4→x86,32位,8→x64,64位
如果使用Visual Studio命令提示符,则应该能够使用dumpbin
。为你的dll做一个dumpbin /headers yourdll.dll | more
。第一行之一应为machine (...)
。在(...)
中,如果是x86(32位)或x64(64位),则应写入
对于第二个问题,你不能以任何方式在一个进程中混合使用32位和64位dll。有些程序“欺骗”并使用正确的位创建辅助进程以加载dll,然后在主进程和辅助进程之间进行IPC(进程间通信)以使用dll。显然它很复杂。