使用 Linux 加载器时出现 ldconfig 错误:“不是符号链接”。

56

运行时:

    sudo /sbin/ldconfig

出现以下错误:

    /sbin/ldconfig: /usr/local/lib/ is not a symbolic link

运行file命令时,会出现以下结果:

    file /usr/local/lib/
    /usr/local/lib/: directory

/usr/local/lib/ 目录下有我使用的三个库,这里称它们为 lib1lib2lib3

现在,当我在我的二进制文件上执行 ldd 命令时,结果如下:

    lib1.so => not found
    lib2.so => not found
    lib3.so => /usr/local/lib/lib3.so (0x00216000)

但是它们全都在同一个文件夹中,路径为/usr/local/lib/{lib1,lib2,lib3}.so.

每次运行ldconfig时,都会出现相同的错误:

/usr/local/lib/ is not a symbolic link

我认为在/etc/ld.conf.d/*.conf中应该声明两次/usr/local/lib,但实际上不需要:

    sudo egrep '\/usr\/local' /etc/ld.so.conf.d/*
    projectA.conf.old:/usr/local/projectA/lib
    local.conf:/usr/local/lib

ld.so.conf 只包括 /etc/ld.so.conf.d/*.conf,因此这个 *.old 没有被处理,并且它指向的是 /usr/local/projectA/lib

试了一段时间后,我删除了所有的 lib1 和 lib2(在某个时候我将其测试在二进制文件夹中),但是仍然出现相同的错误。

7个回答

59

我在使用Oracle 11R2客户端时遇到了这个问题。不确定是Oracle安装程序还是在我到达之前的某个人做的。这与64位和32位无关,全部都是64位。

出现错误的原因是libexpat.so.1不是一个符号链接。

事实证明有两个相同的文件libexpat.so.1.5.2libexpat.so.1。删除有问题的文件并将其作为指向1.5.2版本的符号链接使错误消失。

让老版本库的公共名称是当前版本的符号链接是有道理的。如果这样做,就不太可能会出现旧的库。


他们在离开之前是否共享了相同的md5sum结果? - Rodrigo Gurgel
这不是在你之前有人做的。客户端安装程序会处理这个问题。建议的修复方法有效。 - Avindra Goolcharan
有关libcudnn.so.5,我遇到了相同的问题。它与其他文件完全相同,但会引起ldconfig错误。只需创建符号链接即可解决。您有任何想法为什么会发生这种情况吗? - grisevg
3
我猜你指的是笨拙的安装脚本。 - Dan Pritts
2
这个修复方法适用于许多不同的文件(CUDA 相关文件经常出现此问题)。基本上,删除非符号链接版本并重新创建它,以便它链接到最新版本。因此,在这种情况下,请 cd 到找到该文件的目录,调用 ls -a | grep libexpat,这将显示 libexpat.so.1.5.2libexpat.so.1。调用 rm libexpat.so.1; ln -s libexpat.so.1.5.2 libexpat.so.1。您可能需要使用 sudo 来执行此操作。 - JakeCowton
显示剩余3条评论

10
我只是运行了下面的命令:

export LD_LIBRARY_PATH=/usr/lib/

现在一切正常运作。


6
可以在此加一两句解释吗? - kRazzy R
在RHEL7上安装Oracle 19c时,这个方法对我有用。错误信息是“/sbin/ldconfig: /lib64/libsnmp++.so.33不是符号链接”。 - Anurag Singh
为什么这会是符号链接问题的解决方案?因为它强制将库的搜索路径设置为另一个路径,这样就不会遇到问题了吗?但是缺失的符号链接(例如由于复制而导致)仍然存在... - Déjà vu
1
可能是因为它排除了包含重复文件的路径。 - Dan Pritts

8

至少在提问时的那一刻,问题已经得到解决。

在提问之前我在网上搜索过,但并没有找到确定的解决方案。导致这个错误的原因可能是:lib1.so和lib2.so不正常,很可能不是为64位PC编译的,而是为32位机器编译的,否则lib3.so是一个64位库。至少这是我的假设。

非常不幸的是,ldconfig没有给出清晰的错误消息,告知它无法加载库,它只会输出:

ldconfig:/folder_where_the_wicked_lib_is/ 不是符号链接

当我从二进制文件中删除了ldd未找到的库时,我解决了这个问题。现在我知道问题出在哪里,所以更容易解决了。

我的ld版本: GNU ld version 2.20.51,我不知道更新的版本是否对用户有更好的消息提示。

谢谢。


4

您需要在 /etc/ld.so.conf 中包含库的路径,并重新运行 ldconfig 以更新列表。

另一种可能性是将库路径包含在环境变量 LD_LIBRARY_PATH 中,然后重新运行可执行文件。

检查符号链接是否指向有效的库...

您可以直接在 /etc/ld.so.conf 中添加路径,而无需包含...

运行 ldconfig -p 查看您的库是否已正确包含在缓存中。


路径已经在local.conf中:它的内容是: /usr/local/lib 在ld.so.conf中,包含了特定文件夹内每个file.conf的内容: /etc/ld.so.conf.d/*.conf - Rodrigo Gurgel
你确定它被处理得好吗? - alinsoar
1
运行 ldconfig -p | grep lib[[:digit:]][.]so 命令,检查是否一切正常。这是我能为您提供的全部帮助。 - alinsoar
谢谢,它似乎没有出现,主要问题是无意义的错误/sbin/ldconfig:/usr/local/lib/不是符号链接 对于一个文件夹,当然它不是一个链接? ld在等待一个链接? 为什么它在等待? - Rodrigo Gurgel
我的朋友(正如我在问题中所说),最重要的是错误信息,而这个错误信息发生在我运行ldconfig时。你还需要什么信息? - Rodrigo Gurgel
显示剩余3条评论

3
我也遇到了同样的问题, 解决方法是: 你收到错误提示的文件可能是另一个版本的实际文件的重复文件。只需删除出现错误提示的特定文件即可解决该问题。

0
通常会使用版本。例如,您可以有一个名为lib1.so.1的实际库,它是带有次要版本的库(也可以是补丁版本,如*.so.1.1)。然后,应该有一个指向您的次要(或补丁)版本的“主要”符号链接。像sudo ln -s /usr/local/lib/lib1.so.1 /usr/local/lib1.so这样。
如果您有某个库的补丁版本libsomething.so.1.3,那么您的主要和次要符号链接都应该指向补丁版本。虽然您可以创建符号链接链,例如major -> minor -> patch(或genericmajorspecific,这取决于读者是谁),但“专家”通常不推荐这样做。这只是“意见”。请记住这一点。 /usr/local/lib通常用于自定义的32位库,而/usr/local/lib64用于自定义的64位库。
自定义库是您自己开发的或者您明确(手动)安装在系统上的库。
要知道所使用的库的体系结构,可以使用命令file /usr/local/lib/lib1.so.1。它会告诉您是32位还是64位。因此,您可以将库移动到适当的目录(这不是强制性的,但是一个好的约定)。 /usr/local/{lib,lib64}目录通常不会被ldconfig默认缓存(包含)。您需要“教”ldconfig也缓存这些路径下的库。
为此,您需要编辑/etc/ld.so.conf文件,并添加类似于include ld.so.conf.d/*.conf的行(相对路径)。这实际上告诉ldconfig/etc/ld.so.conf.d/目录加载其他配置文件。
然后,您可以在/etc/ld.so.conf.d/中创建任意数量的ldconfig配置文件,但是一个好的起点可能是/etc/ld.so.conf.d/extra.conf
在这个文件中,你告诉ldconfig应该缓存(包含)哪些其他路径。在我们的情况下,只需添加两行 - /usr/local/lib/usr/local/lib64
完成所有这些后,你只需要使用sudo ldconfig来更新你的共享库缓存。
在大多数情况下,使用LD_LIBRARY_PATH环境变量是一个“仅限开发工具”,当你想要加载一些特定的库时使用。通常情况下,你不应该使用/设置它。
要查看你的库是否已被缓存,你可以使用ldconfig -p | grep libsomelib

0

在shell中简单运行:sudo apt-get install --reinstall libexpat1
使用同样的方法解决了libxcb的问题 - 非常快 :)


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接