问题

示例:我有两个共享对象(同样应该适用于.dlls).第一个共享对象来自第三方库,我们将称之为libA.so.我用JNI包装了其中一些并创建了我自己的库libB.so.现在libB依赖于libA.

当webstart时,两个库都是某个webstart工作区的位置.我的java代码尝试加载libB.此时,系统加载器将尝试加载不在系统库路径中的libA(java.library.path不会帮助这个).最终结果是libB有一个不满意的链接,无法使用.

我已经尝试在libB之前加载libA,但这仍然不起作用.似乎操作系统想为我做这个加载.除了静态编译之外,有没有办法让这个工作?

  最佳答案

我不确定这是否与webstart的方式完全相同,但是在处理一组本机库时,我们在桌面应用程序中遇到了这种情况(在我们的情况下是dlls).

在libB之前加载libA应该工作,除非其中一个库有一个依赖关系,而不是在路径中.我的理解是,一旦它进入系统loadLibrary调用(即Java在其java.library.path中找到了库,现在正在告诉操作系统加载它) – 它完全依赖于操作系统来找到任何依赖的库,因为当时它是加载库进程的操作系统,操作系统只知道如何查看系统路径.在Webastart的情况下,这似乎很难设置,但有办法解决这不涉及静态应用程序的问题.您可能不确定您的库在哪里洗牌 – 我不确定您的库.

如果您使用自定义类加载器,您可以覆盖loadLibrary和findLibrary,以便它可以从类路径中的jar中找到您的库,如果您还让它知道您的本机库依赖项(即libB依赖于libA,然后在加载libB时,您可以捕获自己并确保首先加载libA,并首先检查该通知并加载libX.然后操作系统不会尝试找到不在路径中的库.它是klunky和一点痛苦,但确保Java找到并按正确的顺序加载它们.

  相同标签的其他问题

javajava-native-interfacejava-web-start
上一个问题: