C++ DLL 卸载析构函数?

标签 c++ windows winapi dll

所以我有一个用 C++ 编写的 DLL。 但是,它使用 GlobalAlloc() 分配内存。为避免内存泄漏,我想跟踪这些分配并在 DLL 销毁时取消所有分配。

有什么方法可以编写一个在我的 DLL 被卸载时调用的函数吗? 我能想到的一件事是在我的 DLL 中创建一个全局对象并在其析构函数中编写无内存调用,但这似乎有点矫枉过正。 我的另一个想法是仅依靠操作系统在 DLL 卸载时释放内存,但这看起来很脏。

谢谢

最佳答案

Is there any way to write a function that will be called when my DLL is unloaded? One thing I can think of is creating a global object in my DLL and writing the memory free calls in its destructor

这是可能的,尽管我相信调用对象的析构函数的确切时间是不确定的。

您可能对 DLL_PROCESS_DETACH 感兴趣,虽然您应该避免在 DllMain 中做任何重要的事情,但在这里释放资源似乎是可以接受的。注意注意事项:

When a DLL is unloaded from a process as a result of an unsuccessful load of the DLL, termination of the process, or a call to FreeLibrary, the system does not call the DLL's entry-point function with the DLL_THREAD_DETACH value for the individual threads of the process. The DLL is only sent a DLL_PROCESS_DETACH notification. DLLs can take this opportunity to clean up all resources for all threads known to the DLL.

When handling DLL_PROCESS_DETACH, a DLL should free resources such as heap memory only if the DLL is being unloaded dynamically (the lpReserved parameter is NULL). If the process is terminating (the lpvReserved parameter is non-NULL), all threads in the process except the current thread either have exited already or have been explicitly terminated by a call to the ExitProcess function, which might leave some process resources such as heaps in an inconsistent state. In this case, it is not safe for the DLL to clean up the resources. Instead, the DLL should allow the operating system to reclaim the memory.

您可能需要详细说明为什么您的 DLL 可以保留内存,如果您有许多由 DLL 创建的对象,它们应该有一个定义的生命周期并在它们结束时自行清理生活。

如果它们不是对象(即内存被分配并通过函数返回给调用者)为什么不把责任交还给使用你的 DLL 的人呢?他们可以释放内存。终端服务库遵循这种模式 ( WTSFreeMemory )。

如果资源是长期存在的并且必须在您的库的生命周期内存在,让消费者控制您的库的生命周期。根据需要编写两个函数:MyFrameworkStartupMyFrameworkShutdown。 Winsock 遵循此模式(WSAStartupWSACleanup)。

My other idea is to just rely on the operating system to free the memory when the DLL unloads, but this seems dirty.

You'll be okay if the process is exiting :

Don't worry about freeing memory; it will all go away when the process address space is destroyed. Don't worry about closing handles; handles are closed automatically when the process handle table is destroyed. Don't try to call into other DLLs, because those other DLLs may already have received their DLL_PROCESS_DETACH notifications, in which case they may behave erratically in the same way that a Delphi object behaves erratically if you try to use it after its destructor has run.

在实现“什么都不做”策略之前,请务必阅读整篇文章和评论并理解它。

关于C++ DLL 卸载析构函数?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10158393/

相关文章:

c++ - 80 年代后期的老 friend : What was the emacs-like editor that came with MS C 5. 0(用于 DOS)?

c++ - 为什么我可以使用以 0 大小 : Char ch[0]; 启动的数组

c++ - 简单的客户端/服务器在传输中丢失线路 (boost/Windows)

Windows 命令提示符 - 'debug' 不是可识别的命令?

c++ - CreateFile 函数可以打开仅在 Global 下列出的设备的句柄吗? WinObj 实用程序中的目录?

c# - 如何将字节操作转换为 C#?

c# - 寻找在 WPF 中显示数据行的最简单方法

c++ - 打印作业时,最后的作业状态是 JOB_STATUS_PAUSED,而不是 JOB_STATUS_PRINTED

c++ - Windows 7 资源管理器.exe

c++ - 当 const 未一致使用时,如何使编译器至少发出警告