如何在Linux中使懒惰/延迟加载工作



我在Windows上做得很好——应用程序加载我的插件(C++,Qt),我的插件进行智能搜索以找到已安装的JRE,相应地设置库搜索路径,然后调用JVM中的一个函数,强制在该点加载JVM.dll。(上一个问题:如何部署C++/Java(JNI)混合应用程序?)

现在我正试图让它在Linux上运行。据我所知,懒惰链接/加载是默认的,所以我认为它会起作用。。。。看起来不像。

我想避免使用dlopen()dlsym()LD_LIBRARY_PATHldconfig等。这个想法是,这个插件的用户不应该知道它们是如何工作的,他们只需要把plugin.so放在正确的位置,当它加载时,插件就可以智能地找到JRE(或告诉用户安装JRE)。

这能做到吗?

编辑

只是要明确一点。。。加载插件时我得到的错误是:"无法加载库/home/dan/bah/bah/libMyPlugin.so:(libjawt.so:无法打开共享对象文件:没有这样的文件或目录)"

编辑

如果重要的话。。。这需要在Ubuntu 10.10及更高版本、CentOS 5.4和OSX 10.6+上运行。

在Ubuntu 10.10上,我做了apt-get install openjdk-6-jdk,然后为了让事情正常运行,我不得不使用

export LD_LIBRARY_PATH=
  /usr/lib/jvm/java-6-openjdk/jre/lib/i386:
  /usr/lib/jvm/java-6-openjdk/jre/lib/i386/client:
  /usr/lib/jvm/java-6-openjdk/jre/lib/i386/xawt

(换行以便于阅读)

但是,如果有人安装了不同的JDK(例如Sun),那么目录可能会有所不同(?)。

您是如何在windows上进行智能搜索的?Linux中有几个"正常"的地方。

很多时候,$JAVA_HOME环境变量被设置为当前JRE。

我还没有准备好访问您列出的所有系统,但在一些发行版上,您有一个符号链接/usr/java/relatest,它将指向最新安装的版本。

通常,如果安装了JRE,它可能位于/usr/lib/jvm*、/usr/java*、/usr/lib/java*中的一个,或者可能位于上述lib64变体中的一个中。

当然,上述方法很可能会将您指向JRE。决定使用哪种可能很棘手,但如果你的代码不依赖于最新和最棒的,那可能没问题。

我想,如果找不到JRE,作为要求用户安装JRE的一部分,您可以要求他们设置$JAVA_HOME,因为这是相当标准的做法。

我不知道它在所有发行版上都有什么确切的方法,因为部分问题源于*nix发行版的性质。然而,我可能错过了一个额外的约定。

如果你的程序只是运行java /path/to/foo.jar,那么这个解决方案在Debian派生的系统上很容易:

$ ls -l /usr/bin/java /etc/alternatives/java /usr/lib/jvm/java-6-sun/jre/bin/java | awk '{print $1, $8, $9, $10}'
lrwxrwxrwx /etc/alternatives/java -> /usr/lib/jvm/java-6-sun/jre/bin/java
lrwxrwxrwx /usr/bin/java -> /etc/alternatives/java
-rwxr-xr-x /usr/lib/jvm/java-6-sun/jre/bin/java  
$ 

/usr/bin/java中的java是指向真实JRE的符号链接的符号链接。

最新更新