C# LoadLibrary、FreeLibrary和GetModuleHandle Win32函数是否线程安全?

C# LoadLibrary、FreeLibrary和GetModuleHandle Win32函数是否线程安全?,c#,multithreading,winapi,C#,Multithreading,Winapi,我正在处理一个与本机DLL交互的web服务,我使用LoadLibrary/GetModuleHandle/FreeLIbrary和GetProcAddress动态加载/卸载DLL,因为它不太稳定 public class NativeMethods { [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] public static extern IntPtr LoadLibrary(st

我正在处理一个与本机DLL交互的web服务,我使用LoadLibrary/GetModuleHandle/FreeLIbrary和GetProcAddress动态加载/卸载DLL,因为它不太稳定

public class NativeMethods
{
    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    public static extern IntPtr LoadLibrary(string libname);

    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    public static extern IntPtr GetModuleHandle(string libname);

    [DllImport("kernel32.dll", CharSet = CharSet.Auto)]
    public static extern bool FreeLibrary(IntPtr hModule);

    [DllImport("kernel32.dll", CharSet = CharSet.Ansi)]
    public static extern IntPtr GetProcAddress(IntPtr hModule, string lpProcName); 
}
我注意到w3wp.exe进程有时会在重载下崩溃,当我尝试调试它时,调试器通常会在我的NativeMethods.GetModuleHandle()函数调用时停止

我找不到任何证据表明
GetModuleHandle
不是线程安全的,所以我想知道有没有人在从多线程.NET应用程序交互这些kernel32.dll函数时有过类似的经验


根据Igor Tandetnik(微软MVP)的说法,奥斯卡

除了非线程安全的GDI函数之外。几乎任何接受
HWND
和/或
HDC
的内容都必须在创建
HWND
HDC
的同一线程上调用(
sendmages
PostMessage
和类似的内容是显著的例外)
HBITMAP
s、
HICON
s等可以在线程之间传递,但一次只能由一个线程操作

大多数其他函数——那些不处理GDI或窗口管理的函数——确实是线程安全的

这应该包括
LoadLibrary
GetModuleHandle
FreeLibrary
GetProcAddress

但是请记住,不应从DllMain调用FreeLibrary


我还可以补充一点,我已经在多线程环境中使用这些函数很长时间了,没有问题。

LoadLibrary和FreeLibrary相对于DLL加载列表应该是线程安全的,理论上GetModuleHandle也应该是线程安全的,但是,我可能会使用LoadLibrary/freebrary对,而不是使用该方法,因为这样可以确保您拥有对该库的引用,并且在您使用该库时它不会从内存中消失(如果此人正确)不为MS工作?但他是一名MVP…更改了答案以反映之前的评论请注意,
LoadLibrary
会增加模块的引用计数,而
GetModuleHandle
不会增加模块的引用计数。不幸的是,这使得
GetModuleHandle
不是线程安全的。有关更多详细信息,请参见备注部分:关键说明:例如,假设一个线程检索一个模块句柄,但在它使用该句柄之前,第二个线程将释放该模块。。。。