这是我在 stackoverflow 上的第一个问题,所以我会尽力做好。
Context:
我想提供一个可以在每个 Linux 发行版上运行的程序(例如,一个将使用 C++11 的程序,在没有 C++11 库的系统上运行)。
为此,我想复制我的程序使用的所有库,并将它们放入可执行文件的文件夹中,这样它就可以使用这些库而不是系统的库。
我有2个环境要测试:
- Opensuse,带有(GNU libc)2.19
- Ubuntu,带有(Ubuntu EGLIBC 2.17-Oubuntu5.1)2.17
我在 Opensuse 下编译我的程序,并在 Ubuntu 下运行它。该程序在使用默认库时运行良好。
Project:
这里是main.c:
int main(int ac, char **av) {
printf("Hello World !\n");
}
这是 Opensuse 下我的文件夹树(在 Ubuntu 下相同,没有 main.c 和 exec.sh):
+ project
|
+--- main.c
+--- a.out
+--- exec.sh
+---+ lib
|
+--- libc.so.6
+--- ld-linux-x86-64.so.2
最后,当我通过简单的编译启动程序时,这是 ldd 和 readelf:
> gcc main.c -o a.out
> ldd ./a.out
linux-vdso.so.1 (0x00007fff85f57000)
libc.so.6 => /lib64/libc.so.6 (0x00007f1fdaaaf000)
/lib64/ld-linux-x86-64.so.2 (0x00007f1dae75000)
> readelf -d a.out | grep "library\|Library"
0x0000000000000001 (NEEDED) Shared library: [libc.so.6]
我做了一些研究,最后发现这个帖子 https://stackoverflow.com/questions/847179/multiple-glibc-libraries-on-a-single-host/851229#851229谁解释一下 ld-linux.so。
这是我用来编译的脚本:
#!/bin/bash
dir=`pwd`
execName="a.out"
libDir="/lib"
linker="ld-linux-x86-64.so.2"
gcc main.c -o ${execName} -Wl,--rpath=${dir}${libDir} -Wl,--dynamic-linker=${dir}${libDir}/${linker}
当我在 Opensuse 上启动 a.out 并使用脚本进行编译时,我得到以下信息:
> ./a.out
Hello World !
> ldd ./a.out
linux-vdso.so.1 (0x00007f3222e27000)
libc.so.6 => /path/to/project/lib/libc.so.6 (0x00007f3222a7e000)
/path/to/project/lib/ld-linux-x86-64.so.2 => /lib64/ld-linux-x86-64.so.2 (0x000073222e2b000)
> readelf -d a.out | grep "library\|Library"
0x0000000000000001 (NEEDED) Shared library: [libc.so.6]
0x000000000000001d (RUNPATH) Library runpath: [/path/to/project/lib]
Problem:
现在,当我在 Ubuntu 上启动这个可执行文件 a.out(在 Opensuse 下编译)时,我得到以下输出:
> ./a.out
./a.out: Permission denied.
> ldd ./a.out
linux-vdso.so.1 (0x00007fff5b5fe000)
libc.so.6 => /path/to/project/lib/libc.so.6 (0x00007f47df480000)
/path/to/project/lib/ld-linux-x86-64.so.2 => /lib64/ld-linux-x86-64.so.2 (0x00007f47df82a000)
> readelf -d a.out | grep "library\|Library"
0x0000000000000001 (NEEDED) Shared library: [libc.so.6]
0x000000000000001d (RUNPATH) Library runpath: [/path/to/project/lib]
当我启动可执行文件时,此权限一直被拒绝,我不知道为什么。
我使用 Filezilla 将 a.out 和 lib 文件夹从 Opensuse 转移到 Ubuntu,并且 a.out 在转移后不是可执行文件,因此我需要执行以下操作:
chmod 755 a.out
我在 Opensuse 和 Ubuntu 下有相同的树
2个图书馆在lib文件夹是 Opensuse 的默认库
任何有关被拒绝的许可的帮助,或者以其他方式做我想做的事情都将受到欢迎。
在此先感谢您的帮助!
注意:我不能使用 LD_PRELOAD,因为你需要 root 才能使用它,所以它无法完成我想要做的事情。
另外我想避免静态编译,但如果这是唯一的解决方案我会考虑它