【发布时间】:2013-09-17 14:22:38
【问题描述】:
我有一个加载到 C# Windows 窗体应用程序中的 C++ DLL。我正在尝试使用 dll 创建一个 opengl 上下文,并在卸载/重新加载 dll 时保留它以供在托管应用程序中使用。我正在使用 LoadLibrary 和 FreeLibrary 来加载 DLL。
这可能吗?如果 C++ DLL 加载 opengl DLL,如果我在加载它的 DLL 上调用 FreeLibrary,opengl dll 会被卸载吗?将由 c++ DLL 创建的非托管对象存储在托管代码中并在该 DLL 的新实例中重用它们是否安全?
【问题讨论】:
-
几乎可以肯定这是不可能的。
-
哪一部分?因为我曾尝试使用 C++ DLL 和 C++ 应用程序从未加载的 DLL 中保留数据,并且在重新加载 DLL 后数据可用。我没有尝试使用 opengl 上下文,但我看不出情况会有任何不同的任何原因。我想我应该用 OpenGL 尝试同样的旧 C++ 到 C++ 测试应用程序来确认。
-
我不希望从卸载的 DLL 中保留数据真的有效。如果其中一些数据涉及全局结构怎么办?那么堆呢?只要堆驻留在不同的模块中,您就可以摆脱它。无论如何,只有您知道您的 DLL 实际在做什么。只有你知道这些信息是什么。你不能指望我们对此一无所知。
-
“那么堆呢”——在我之前问的一个问题中,有人告诉我DLL分配的内存属于进程,而不是DLL,这样以后可以安全地重用它DLL 被卸载。这是不真实的吗?我的最后一个测试用例是不是运气好,只是因为内存还没有被覆盖? “如果其中一些数据涉及全球结构怎么办?” - 我检查了我的 DLL,并试图确保我引用的数据结构没有指向全局数据的指针。有可能,但不太可能我错过了。
-
@AlBundy:内存属于进程,但数据结构属于DLL。如果你试图将一个分配在一个 DLL 中的对象传递给另一个 DLL 中的释放函数,它会变得非常混乱。即使它是同一个DLL,也只是第二次加载。因为当你重新加载它时,它的“所有分配的块”列表会重新开始。