在 Debian 上启动 java 时出现问题:“加载共享库时出错:libjli.so”

在 Debian 上启动 java 时出现问题:“加载共享库时出错:libjli.so”

我正在尝试启动java:

$ java -version
java: error while loading shared libraries: libjli.so: cannot open shared object file: No such file or directory

$ ldd /usr/lib/jvm/java-6-openjdk/jre/bin/java
        linux-gate.so.1 =>  (0xb779f000)
        libz.so.1 => /usr/lib/libz.so.1 (0xb7780000)
        libpthread.so.0 => /lib/i686/cmov/libpthread.so.0 (0xb7767000)
        libjli.so => /usr/lib/jvm/java-6-openjdk/jre/bin/../lib/i386/jli/libjli.so (0xb7762000)
        libdl.so.2 => /lib/i686/cmov/libdl.so.2 (0xb775e000)
        libc.so.6 => /lib/i686/cmov/libc.so.6 (0xb7603000)
        /lib/ld-linux.so.2 (0xb77a0000
$ ls /usr/lib/jvm/java-6-openjdk/jre/bin/../lib/i386/jli/
libjli.so

但java在root下工作:

$ sudo java -version
java version "1.6.0_18"
OpenJDK Runtime Environment (IcedTea6 1.8.7) (6b18-1.8.7-2~lenny1)
OpenJDK Client VM (build 14.0-b16, mixed mode, sharing)

更新:

/usr/lib/jvm/java-6-openjdk/jre/bin/java 实际上是我的 java 命令:

$ type java
java is hashed (/usr/bin/java)
$ ls -l /usr/bin/java
lrwxrwxrwx 1 root root 22 Jul 14 10:15 /usr/bin/java -> /etc/alternatives/java
$ ls -l /etc/alternatives/java
lrwxrwxrwx 1 root root 40 Jul 14 10:36 /etc/alternatives/java -> /usr/lib/jvm/java-6-openjdk/jre/bin/java

更新2:

我还尝试设置根路径:

$ sudo su
# echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
# exit
$ export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
$ java -version
java: error while loading shared libraries: libjli.so: cannot open shared object file: No such file or directory

更新3:

我试过了:

# comm -3 <(declare | sort) <(declare -f | sort)

在根下。但是java没有可用的环境变量。

UPD4:

strace -f java -version结果:http://dumpz.org/67368/

答案1

open("$ORIGIN/../lib/i386/jli/tls/i686/sse2/cmov/libz.so.1", O_RDONLY) = -1 ENOENT (No such file or directory)

您正在运行的可执行文件在以下位置查找库路径除了正常的库搜索路径之外。这里的 rpath 是$ORIGIN/../lib/i386/jli:$ORIGIN/../jre/lib/i386/jli.通常$ORIGIN应替换为可执行文件的位置,此处为/usr/lib/jvm/java-6-openjdk/jre/bin

在这里,$ORIGIN不会被替换。在使用额外权限(setuid、setgid 或 setpcap)运行的可执行文件中,该功能被关闭,因为否则你可能会注入不同的库,从而以提升的权限运行任意代码。(参见本文以获得更详细的解释。)安全问题是最近才发现的;在 Debian 中它被修复了DSA-2122-1,因此在升级到 之前libc6-2.7-18lenny6,您的java可执行文件可能已经工作了。

该症状表明正在java以附加权限运行。正常 Debian 安装中不会出现这种情况。确保/usr/lib/jvm/java-6-openjdk/jre/bin/java模式为 755 并且没有任何功能(getcap /usr/lib/jvm/java-6-openjdk/jre/bin/java,并setcap -r …删除功能(如果有))。


java(原始答案,如果您发现以 root 身份工作但不能以其他用户身份工作,并且事实证明您正在调用不同的二进制文件,这可能很有用。)

我敢打赌,您的(更改)java之前有其他版本。检查一下内容- 可能是报告的某个不同的 Java 版本。PATHsudoPATHtype javaldd /path/to/bin/javalibjli.so => not found

我推测这个Java版本找不到的原因libjli.so是它通过rpath(存储在可执行文件中的库搜索路径)寻找它,该路径与它的安装方式不匹配。如果java二进制文件位于 中/some/where/bin/java,并且它具有相对 rpath(这是 Sun JDK 和 OpenJDK 的方式),则该库应该位于 中/some/where/lib/i386/jli/libjli.so(假设 i386 架构)。如果 rpath 是绝对路径,则需要放入libjli.so确切的指定位置,或者设置LD_LIBRARY_PATH为包含所在libjli.so位置。

答案2

我从java.com下载了“1.7.0_60”.tar.gz格式并将其安装到/usr/local/jre1.7.0_60.然后我创建了一个硬链接/usr/local/bin/java并收到了上述错误。

将硬链接更改为符号链接解决了该问题。

简洁版本:

$ sudo ln /usr/local/jre1.7.0_60/bin/java /usr/local/bin/java

不好。

$ sudo ln -s /usr/local/jre1.7.0_60/bin/java /usr/local/bin/java

很好。

答案3

尝试在同一路径中找到 java 可执行文件libjli.so并使用它。

例如我发现libjli.so/usr/lib/jvm/java-7-oracle/jre/lib/amd64/jli/libjli.so,所以我用了

find /usr/lib/jvm/java-7-oracle/ -name "java"

并在 中找到了可执行文件/usr/lib/jvm/java-7-oracle/bin/java。然后,我删除了java上面/usr/bin的可执行文件并将其符号链接到/usr/bin.

答案4

检查该文件的权限。它们应该看起来像0644/-rw-r--r--。如果没有,请重新安装openjdk-6-jre-headless,因为这意味着有人搞乱了权限。

相关内容