使用RPATH而不是RUNPATH?

这个页面 – http://labs.qt.nokia.com/2011/10/28/rpath-and-runpath/ – 介绍了在ld.so中库search的顺序:

Unless loading object has RUNPATH: RPATH of the loading object, then the RPATH of its loader (unless it has a RUNPATH), ..., until the end of the chain, which is either the executable or an object loaded by dlopen Unless executable has RUNPATH: RPATH of the executable LD_LIBRARY_PATH RUNPATH of the loading object ld.so.cache default dirs 

然后build议:

运送二进制文件时,请使用RPATH而不是RUNPATH,或者确保在运行之前设置LD_LIBRARY_PATH。

因此,使用RPATHRUNPATH是不好的,因为RUNPATHtypes取消了RPATH所以间接dynamic加载不能按预期工作? 但是为什么RPATH不赞成RUNPATH呢?

有人可以解释这种情况吗?

当你发布一个二进制文件时,最好给用户提供一些手段来调整二进制文件到他们自己的系统的特性中去,尤其是调整库的搜索路径。

用户通常可以调整LD_LIBRARY_PATH/etc/ld.co.conf ,两者的优先级都低于DT_RPATH ,即不能覆盖二进制文件中硬编码的内容,而如果使用DT_RUNPATH代替,则用户可以覆盖它与LD_LIBRARY_PATH。

(FWIW,我认为ld.so.conf也应该优先于DT_RUNPATH ,但无论如何,至少我们有LD_LIBRARY_PATH )。

另外,我坚决不同意使用DT_RPATH的建议。 国际海事组织,它最好使用运送的二进制文件中的DT_RPATH而不是DT_RUNPATH

除非

您将所有依赖库与您的可执行文件一起发送,并希望在安装之后确保JustWork(tm),在这种情况下使用DT_RPATH

寒意的答案是完全正确的; 我想简单地添加一些颜色,从最近的glibc源代码读取([master 8b0ccb2],2.17)。 要清楚的是,如果在给定级别指定的位置没有找到库,则尝试下一级。 如果在给定级别找到了一个库,搜索将停止。

动态图书馆搜索顺序:

  1. ELF二进制文件中的DT_RPATH,除非设置了DT_RUNPATH。
  2. LD_LIBRARY_PATH条目,除非setuid / setgid
  3. ELF二进制文件中的DT_RUNPATH
  4. /etc/ld.so.cache条目,除非-z nodeflib在链接时给出
  5. / lib,/ usr / lib除非-z nodeflib
  6. 完成,“找不到”。

但是为什么RPATH不赞成RUNPATH呢?

引入DT_RPATH时,优先于所有其他参数。 即使出于开发目的,这也使得不可能覆盖库搜索路径。 因此,引入了另一个参数LD_RUNPATH,其优先级低于LD_LIBRARY_PATH。

更详细的信息可以在Ulrich Drepper 编写的“如何编写共享库”一书中找到。