为啥有这么多符号链接?

Posted

技术标签:

【中文标题】为啥有这么多符号链接?【英文标题】:Why so many symbolic links?为什么有这么多符号链接? 【发布时间】:2015-02-06 12:24:02 【问题描述】:

安装 Opencv 2.4.9 后,我发现它在 /usr/local/lib 中创建了许多符号链接。说,对于libopencv_core.so.2.4.9,当我使用ls -l时,它显示了

...
libopencv_core.so -> libopencv_core.so.2.4
libopencv_core.so.2.4 -> libopencv_core.so.2.4.9
libopencv_core.so.2.4.9
...

我的问题是,既然它已经将真正的共享库 libopencv_core.so.2.4.9 放在 /usr/lcoal/lib 中,为什么还要创建指向它的符号链接,甚至创建指向该符号链接的另一个符号链接?

将真正的共享库放在其他地方并在 /usr/local/lib 中建立指向它们的符号链接会更好吗?

【问题讨论】:

搜索词:“soname” 如果您安装了多个版本并使用需要不同版本的应用程序,这将更明显。 【参考方案1】:

第二个 libopencv_core.so.2.4(别名“soname”)和第三个 libopencv_core.so.2.4.9(别名“真实姓名”)文件允许您更新库(在本例中为 OpenCV)并且仍然支持想要使用这些库的旧版本的程序。

$ ldd a.out libopencv_core.so.2.4 => /path/to/lib/libopencv_core.so.2.4

运行ldd,您可以看到可执行文件未链接到“实名”库? 原因:处理库升级。考虑两种情况。

    具有向后兼容性的库升级 => 安装程序(或 ldconfig)可以更新现有的“soname”链接(例如 libopencv_core.so.2.4)以指向更新的“实名”库(例如 libopencv_core.so.2.4 .10 ) 和我们的旧可执行文件现在将加载升级后的库。 没有向后兼容性的库升级 => 安装程序将创建新的“soname”链接(例如 libopencv_core.so.3.0)以指向新的“实名”库(例如 libopencv_world.so.3.0.0)。此后在此处构建的程序可以链接到较新的库,而较旧的程序将继续加载较旧的 soname (libopencv_core.so.2.4) 指向的库。

关于,第一个符号链接 libopencv_core.so(别名“链接器名称”)用于链接器。对于-lopencv_core 之类的标志,gcc 在库名称和搜索后添加 lib 前缀和 .so 后缀。所以它需要一个名为 libopencv_core.so 的文件,因此需要第一个符号链接。它在程序运行时从不使用。此外,如果愿意将“soname”链接作为 gcc 命令行参数而不是 -lopencv_core,您将永远不需要此软链接。

在这里更好地解释(1)。

【讨论】:

【参考方案2】:

这是在 Linux 系统上非常常用的过程,因为它允许您更改 .so 的最新版本(在您的情况下为 .so.2.4.9),而运行的应用程序只知道它们需要与第一个 .so 链接。所以。

所以所有程序都在加载第一个 .so ,然后通过符号链接最终加载当前安装的版本。

如果按照您的建议进行(只需复制硬.so),那么所有程序都会抱怨他们找不到合适的版本(在您的情况下为 2.4.9)。也许将来你会将你的 openCV 升级到 2.4.10,你的所有程序都将停止工作。

一些项目实际上强制链接到某些主要或中等版本。因此,例如,如果您只保证您的程序适用于 2.4 版本,您会将其链接到 .so.2.4 而不是 .so 。

最后它只是帮助分配兼容性。

【讨论】:

以上是关于为啥有这么多符号链接?的主要内容,如果未能解决你的问题,请参考以下文章

为啥我们通过链接阶段仍然错过符号?

为啥我的符号链接没有链接,而是在我试图链接的目录中创建一个文件

为啥 emacs 会为修改过的文件创建临时符号链接?

为啥 Ambari 集群设置在 zookeeper 安装时失败并出现符号链接错误?

为啥我部署的 Laravel 8 应用程序无法通过符号链接在存储目录中找到图像?

通过 rpmbuild 打包符号链接?