java中dll的可靠卸载

java中dll的可靠卸载,java,dll,java-native-interface,Java,Dll,Java Native Interface,我正在尝试卸载java中的dll。我已经读过了,但是你似乎不能保证dll会在某个特定的时间被卸载。这是因为System.gc()只是“善意地”请求垃圾收集器运行 因此,这里是一个细分的情况。我有一个dll,它通过JNI提供一些功能。让我们调用这个dll MainDll。MainDll是通过调用System.load(“MainDll”)加载的。我需要能够卸载和加载这个动态链接库 是否可以创建另一个仅用于加载和卸载MainDll的dll。让我们调用此dll LoaderDll。然后,我可以简单地调

我正在尝试卸载java中的dll。我已经读过了,但是你似乎不能保证dll会在某个特定的时间被卸载。这是因为System.gc()只是“善意地”请求垃圾收集器运行

因此,这里是一个细分的情况。我有一个dll,它通过JNI提供一些功能。让我们调用这个dll MainDll。MainDll是通过调用System.load(“MainDll”)加载的。我需要能够卸载和加载这个动态链接库

是否可以创建另一个仅用于加载和卸载MainDll的dll。让我们调用此dll LoaderDll。然后,我可以简单地调用System.load(“LoaderDell”)并使用一些本机函数来加载和卸载MainDll。这样做的原因是,我可以访问本机系统上可以动态加载和卸载dll的函数。最棘手的是,如果MainDll是从LoaderDll内部加载的,那么我仍然能够访问我在MainDll中编写的本机函数

抱歉,如果这是一个令人困惑的问题。这似乎有点难以解释


谢谢

如果您需要动态加载和卸载代码,您考虑过OSGi吗。至少在费利克斯是这样


在Oracle/Sun的JDK中,System.gc()将触发一个完整的gc(除非它在命令行上被关闭)。这可能只是对其他JVM的一个提示。

添加一个间接级别


在LoaderDell中创建本机方法调用转发例程。转发例程可以使用C工具转发对mainDLL中代码的调用。

创建一个进行加载/卸载的包装DLL。在DLL中也有包装器方法,这些方法将调用转过来并委托给加载的MainDll。这样,Java JNI代码只知道一个DLL。它仍然可以请求卸载[LoaderDell::unload()],该卸载会在内部卸载MainDll

只要LoaderDell中的方法/函数在当前未加载MainDll时被调用时能够触发MainDll的加载,就应该可以这样做,假设这是所需的行为,而不是引发异常/错误


这样做的一个问题是LoaderDll总是被加载的

根据您澄清的评论,我认为最简单的方法是生成一个新的JVM,它的唯一职责是管理您的DLL。可能会公开一个RMI接口来访问这些类(虽然一个简单的流可能就足够了)。

我还没有遇到过System.gc()不触发垃圾收集器的情况,尽管这只是一个提示。
本教程实际上帮助我完成了我的工作:

您想用这种方法解决什么问题?(除了确定性加载和卸载之外,是否还有其他方法,只是为了获得更好的想法)为什么您需要能够动态加载/卸载MainDLL?通常,当DLL作为构建的一部分部署时,加载/卸载问题会在开发场景中出现。这是您的情况,还是您有其他原因?这是一个视频会议应用程序。我想卸载它有几个原因。通话结束后,有很多不同的事情需要清理。可能会出问题。例如,如果H.323堆栈中存在问题。如果驱动程序已可靠损坏,或者应用程序无法按预期运行,我需要确保可以卸载并重新加载驱动程序。System.gc(),即使在sun jdk上,仍然只是一个问题hint@ChristopherDancy“暗示”就是这样做的。