Linux C++ trys使用绝对路径加载一个特定的库,而所有的其他使用相对一个链接

Linux C++ trys使用绝对路径加载一个特定的库,而所有的其他使用相对一个链接

问题描述:

我有以下问题:我试图创建我的程序的可移植版本,所以我将rpath设置为“ “。所以所有库都使用相对文件路径进行链接。除了一个之外,这对所有图书馆都有效。出于某种原因,只有当一个特定的库存在于编译时所链接的相同位置时,该程序才能正常工作。这是我自己写的,它的路径也设置为“。”。基本上,即使图书馆与可执行文件的位置完全相同,该程序也会拒绝启动。
我已验证只有那一个库是问题,因为如果我在测试计算机上创建了我的计算机上的库文件夹,程序将启动。Linux C++ trys使用绝对路径加载一个特定的库,而所有的其他使用相对一个链接

linux-vdso.so.1 => (0x00007ffcc5961000) 
libOgreHlmsPbs.so.2.1.0 => ./libOgreHlmsPbs.so.2.1.0 (0x00007fedeec3f000) 
libOgreHlmsUnlit.so.2.1.0 => ./libOgreHlmsUnlit.so.2.1.0 (0x00007fedeea1d000) 
libOgreMain.so.2.1.0 => ./libOgreMain.so.2.1.0 (0x00007fedee194000) 
/home/marvin/workspace/HLMS_DS_DEMO/libHLMS_DS.so => not found 

那么有没有人有一个想法是什么可能导致linux试图在原始位置找到库而不是像所有其他位置?此外,该程序在Windows上工作正常。

+0

是否要设置相对于当前目录('$ PWD')的rpath或相对可执行位置? – yugr

+0

为什么不只是遵循 - 我的规则? [GCC目录选项](https://gcc.gnu.org/onlinedocs/gcc/Directory-Options.html#Directory-Options) – Ripi2

+0

相对最佳的可执行位置 – user2741831

我设置的是rpath到.因此所有的库链接使用相对路径

使用. rpath中是一个贫穷的想法:

  • 可用性:应用程序必须从运行一个特定的工作目录。
  • 安全性:攻击者可能会将修改后的.so文件放在另一个目录中,然后从此处运行您的应用程序。

正确的方法是使用-rpath=$ORIGIN功能。见man ld.so

$ ORIGIN(或等效$ {ORIGIN}) 这扩展到包含程序或共享对象的目录。因此,位于somedir /应用的应用程序可以与

gcc -Wl,-rpath,'$ORIGIN/../lib' 

以便找到在somedir/lib中相关联的共享对象不管somedir位于目录层次编译。这有助于创建不需要安装到特殊目录中的“交钥匙”应用程序,但可以解压缩到任何目录中,并仍然可以找到它们自己的共享对象。

$ORIGIN语法是有点可惜,因为它得到双方makebash为变量展开,所以您可能需要适当地引用它。


什么可能导致Linux的试图找到在原始位置的库,而不是在所有其他

当链接像相对之一,该库可以被指定为-lmylib-l:libmylib.so-l<path>/libmylib.so。在后一种情况下,运行时链接程序仅在该特定路径<path>/libmylib.so中查找库。有关完整的详细信息,请参阅man ld,选件-l。您可能想要查看您的构建系统链接器命令。

+0

我使用eclipse cdt,所以我会看看输出。感谢您的帮助 – user2741831

+0

这没有帮助,我想要一个便携式应用程序,这意味着用户需要能够将文件夹放在任何他想要的位置并执行该程序。它在内部使用,所以不用担心,我会看看你的答案的其余部分,看看是否有帮助 – user2741831

+0

我只是试过Ldd,但奇怪的是,每一个其他库都是动态加载的,而我的加载绝对路径,我发布了输出 ... – user2741831