【问题标题】:JNI problem when calling a native library that loads another native library调用加载另一个本机库的本机库时出现 JNI 问题
【发布时间】:2010-04-07 04:12:14
【问题描述】:

我遇到了一个奇怪的问题。我有一个 C++ 项目,它基本上是第三方 DLL 的包装器,如下所示:

我的图书馆
--加载 DLL_A
----加载DLL_B

我使用 LoadLibrary() 加载 DLL_A,包装它的几个函数并生成我自己的 DLL。我已经在 C++ 项目和 C# 项目中对此进行了测试。两者都做了他们应该做的所有事情:加载 DLL_A,进行几个函数调用,并间接加载 DLL_B。问题是当我为 java 构建一个 DLL 并通过 JNI 进行调用时。一切都按预期运行(没有 java.lang.UnsatisfiedLinkError),但是当 DLL_A 加载 DLL_B 时它不起作用。 从调试开始,DLL_B 的加载发生在 DLL_A 中接受回调的函数调用上。当从 Java 调用时,这个函数调用似乎失败(函数指针很好,实际调用顺利进行),我得到一个奇怪的弹出窗口,说 DLL_B 加载失败,我的程序正在等待一个永远不会发生的回调。我可以很好地显式加载 DLL_B(来自 Java 和 C++),并且我检查了所有可能的路径、路径变量,并尝试将 dll 放置在任何地方,看看它是否看起来很有趣。我很确定这不是路径问题。

最终我不知道 DLL_A 是如何加载 DLL_B 的,我不明白为什么在 C++ 和 C# 中一切正常,但在 Java 中却不行。我完全糊涂了。它仍然可能是特定于我的设置的东西(尽管我已经尽力而为),但我将这个场景扔在那里看看是否有人遇到了类似的问题。

-戴夫

【问题讨论】:

    标签: java dll linker java-native-interface


    【解决方案1】:

    实际上只有两种方法可以让一个 DLL 在 Windows 中加载另一个 DLL - 要么使用LoadLibrary() 显式加载,要么通过将第一个 DLL 链接到第二个的导入库来隐式加载。您应该能够使用Dependency Walker 来确定 DLL_B 是否是 DLL_A 的依赖项。运行 depwalker 还会显示 DLL_B 是否在路径上(如果它是隐式链接的)。

    我还将在 DLL_B 上运行 depwalker 以确保 DLL_B 没有令人惊讶的依赖项 - 您看到的问题很可能是由于 DLL_B 无法加载其依赖项之一,而不是 DLL_A 找不到DLL_B。

    IIRC Windows 将扫描 PATH 以查找隐式链接库,因此请检查您对 java 进程的调用是否与该路径一起使用。 LoadLibrary 的文档解释了 LoadLibrary 如何扫描 DLL。

    您说您设法直接从 Java 加载 DLL_B;当你这样做然后通过 DLL_A 调用时,回调机制是否开始工作?暂时这可能是一个有点丑陋的解决方法。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-02-01
      • 2018-07-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-05-25
      相关资源
      最近更新 更多