我正在尝试在二进制文件中指定rpath.我的makefile看起来像这样 -
CC=gcc
CFLAGS=-Wall
LDFLAGS= -rpath='../libs/'
main: main.c
gcc -o main main.c
clean:
rm -f main main.o
Run Code Online (Sandbox Code Playgroud)
但是当我使用命令查询rpath时,我readelf -a ./main | grep rpath没有得到任何东西我已经尝试指定rpath,LDFLAGS= "-rpath=../libs/"但即使这似乎也不起作用.
有人可以发一个例子来说明我应该如何在makefile中指定rpath?
GCC和ld版本是 -
gcc (Ubuntu/Linaro 4.5.2-8ubuntu4) 4.5.2
GNU ld (GNU Binutils for Ubuntu) 2.21.0.20110327
Run Code Online (Sandbox Code Playgroud) 构建二进制文件或库时,指定rpath,即
-Wl,rpath,<path/to/lib>
Run Code Online (Sandbox Code Playgroud)
告诉链接器在二进制文件的运行时在哪里找到所需的库.
什么是关于绝对路径和相对路径的UNIX哲学?使用绝对路径是否更好,以便可以从任何地方找到lib?或者是否更好地使它相对,因此复制整个目录或重命名更高级别的路径不会使二进制文件无法使用?
使用$ORIGIN通常是构建二进制文件的首选方法.对于我喜欢放入绝对路径的库,因为否则你将无法链接到库.符号链接将更$ORIGIN改为指向链接的路径而不是链接目标的路径.
我正在尝试编写一个使用libhdf5的matlab mex函数; 我的Linux安装提供了libhdf5-1.8共享库和头文件.但是,我的Matlab版本r2007b提供了1.6版本的libhdf5.so.(matlab .mat文件bootstrap hdf5,显然).当我编译mex时,它在Matlab中会出现段错误.如果我将我的libhdf5版本降级到1.6(不是长期选项),代码编译并运行正常.
问题:我该如何解决这个问题?如何告诉mex编译过程链接/usr/lib64/libhdf5.so.6而不是/opt/matlab/bin/glnxa64/libhdf5.so.0?当我尝试-Wl,-rpath-link,/usr/lib64在我的编译中使用时,我得到的错误如下:
/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/../../../../x86_64-pc-linux-gnu/bin/ld: warning: libhdf5.so.0, needed by /opt/matlab/matlab75/bin/glnxa64/libmat.so, may conflict with libhdf5.so.6
/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/../../../../lib64/crt1.o: In function `_start':
(.text+0x20): undefined reference to `main'
collect2: ld returned 1 exit status
mex: link of 'hdf5_read_strings.mexa64' failed.
make: *** [hdf5_read_strings.mexa64] Error 1
Run Code Online (Sandbox Code Playgroud)
ACK.最后一种方法是下载hdf5-1.6.5标题的本地副本并完成它,但这不是未来的证明(Matlab版本升级是我的未来.).有任何想法吗?
编辑:根据Ramashalanka的优秀建议,我
A)要求mex -v获得3个gcc命令; 最后一个是链接器命令;
B)用a -v来调用该链接器命令来获取collect命令;
C)调用它collect2 -v -t和其余的标志.
我输出的相关部分:
/usr/bin/ld: mode elf_x86_64
/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/../../../../lib64/crti.o
/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/crtbeginS.o
hdf5_read_strings.o
mexversion.o
-lmx (/opt/matlab/matlab75/bin/glnxa64/libmx.so)
-lmex (/opt/matlab/matlab75/bin/glnxa64/libmex.so)
-lhdf5 (/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/../../../../lib64/libhdf5.so)
/lib64/libz.so
-lm (/usr/lib/gcc/x86_64-pc-linux-gnu/4.3.4/../../../../lib64/libm.so) …Run Code Online (Sandbox Code Playgroud) 我有一个可执行文件隐式加载几个.so库,所有这些都由我构建.对于部署,或至少测试/调试,我想将它们全部放在同一目录中:
my_executable
libmylib1.so
libmylib2.so
Run Code Online (Sandbox Code Playgroud)
为了让可执行文件隐式加载库,我想为可执行文件的目录设置一个rpath(DT_RUNPATH).使用OS X,我会这样做:
clang -dynamiclib -o libmylib1.dylib -install_name @rpath/libmylib1.dylib src1.c src2.c
clang -dynamiclib -o libmylib2.dylib -install_name @rpath/libmylib2.dylib src3.c src4.c
clang -o my_executable -L. -llibmylib1.so -llibmylib2.so -Wl,-rpath,@loader_path/. main.c
Run Code Online (Sandbox Code Playgroud)
请注意,@loader_path/.它在OS X中构成了可执行文件的rpath.对于Linux,我最接近的就是
gcc -dynamiclib -o libmylib1.so src1.c src2.c
gcc -dynamiclib -o libmylib2.so src3.c src4.c
gcc -o my_executable -L. -llibmylib1.so -llibmylib2.so -Wl,-rpath=. main.c
Run Code Online (Sandbox Code Playgroud)
这里的问题是在Linux上,rpath遵循当前的工作目录,而不是可执行文件的目录.有没有办法在Linux上完成同样的事情?
我有一个应用程序,称之为Animal.app.Contents/Frameworks比如,它的文件夹里面是一个框架Mammal.framework.Versions/A/Frameworks在框架的文件夹中,我有dog.dylib.安装名称dog.dylib是@ rpath/dog.dylib.对于"Runpath Search Paths"框架的设置,我已经指定了@loader_path/../Frameworks.(我对最后一个设置的推理是dylib的"loader"将是路径的框架的二进制文件Mammal.framework/Versions/A/Mammal.)
我在运行时收到一条错误消息:
Dyld Error Message:
Library not loaded: @rpath/dog.dylib
Referenced from: /Volumes/VOLUME/*/Animal.app/Contents/MacOS/../Frameworks/Mammal.framework/Versions/A/Mammal
Reason: image not found
Run Code Online (Sandbox Code Playgroud)
我已经阅读了Apple的"Run-Path Dependent Libraries"文档和Mike Ash的博客文章@rpath,但我仍然看不出我做错了什么.
我有一个Linux Qt程序.我希望它优先使用可执行文件目录中的(动态)Qt库(如果存在),否则使用系统的Qt库.RPATH来救援.
我将此行添加到qmake的.pro文件中:
QMAKE_LFLAGS += '-Wl,-rpath,\'\$$ORIGIN\''
Run Code Online (Sandbox Code Playgroud)
用readelf查看生成的可执行文件,我看到:
0x000000000000000f (RPATH) Library rpath: [$ORIGIN:/usr/local/Trolltech/Qt-5.2.0/lib]
0x000000000000001d (RUNPATH) Library runpath: [$ORIGIN:/usr/local/Trolltech/Qt-5.2.0/lib]
Run Code Online (Sandbox Code Playgroud)
似乎没错,但ldd显示它使用的是系统版本:
libQt5Core.so.5 => /usr/local/Trolltech/Qt-5.2.0/lib/libQt5Core.so.5 (0x00007f2d2fe09000)
Run Code Online (Sandbox Code Playgroud)
如果我手动编辑qmake生成的Makefile来交换两个rpath的顺序,那么$ ORIGIN出现在/ usr/local/...之后,我得到了正确的行为:
0x000000000000000f (RPATH) Library rpath: [/usr/local/Trolltech/Qt-5.2.0/lib:$ORIGIN]
0x000000000000001d (RUNPATH) Library runpath: [/usr/local/Trolltech/Qt-5.2.0/lib:$ORIGIN]
libQt5Core.so.5 => ./libQt5Core.so.5 (0x00007fb92aba9000)
Run Code Online (Sandbox Code Playgroud)
我的问题是qmake如何构造最终的LFLAGS变量.我无法弄清楚如何使它在系统库之后添加($ ORIGIN).有任何想法吗?
我一直在尝试使用以下rpath编译openssl 1.0.0g:
$ORIGIN/../lib64
Run Code Online (Sandbox Code Playgroud)
每次我readelf -d apps/openssl,我得到的结果如下,取决于我尝试的逃避变化:
\RIGIN/../lib64
RIGIN/../lib64
ORIGIN/../lib64
Run Code Online (Sandbox Code Playgroud)
我想在不使用像chrpath这样的外部工具的情况下设置我的rpath.它可能吗?我基本上会接受任何不涉及使用像chrpath这样的外部工具的东西(虽然我已经完成了).
理想情况下,我想通过在命令行(任何形式-Wl,-rpath,$ORIGIN/../lib64)上传递选项来实现.
我不介意编辑生成的Makefile,这是我最后一次尝试的.如果我能打印出一个愚蠢的美元符号!我尝试在BUILDENV =块下修改LIBRPATH而没有运气.到目前为止我的最好成绩:
LIBRPATH=$$'ORIGIN/../lib64 # result: /../lib64
LIBRPATH=$$$$'ORIGIN/../lib64 # result: 12345<pid>/../lib64
Run Code Online (Sandbox Code Playgroud)
我已经阅读了各种与rpath相关的问题,并尝试了各种转义和引用技巧但到目前为止没有任何工作!
如果共享库链接到二进制文件,并且共享库还依赖于其他库,那么共享库的 RPATH 和二进制文件的 RPATH 的优先级(链接器搜索顺序)是什么?二进制文件的 RPATH 能否覆盖共享库中的 RPATH?我在共享库 RPATH 中设置的 $ORIGIN 是指 lib 位置还是二进制位置?
提前致谢。
该rpath可执行文件的指定一个或多个目录,其中寻找共享对象在运行时.
我的问题是 - 共享对象文件本身也有静态编译的rpaths?
我最近在与共享对象链接时收到了运行时错误:
./example: /opt/swt/lib64/libstdc++.so.6: version `GLIBCXX_3.4.15' not found (required by ./mylib.so)
Run Code Online (Sandbox Code Playgroud)
这个错误告诉我实际的库本身 - mylib.so有一个静态编译rpath.
我的理解是,rpath只应用于可执行文件,而不是共享对象.那么rpath 也适用于共享对象?
我们使用 MobSF 测试了我们的一款 iOS 应用程序,报告强调该二进制文件已设置运行路径搜索路径 (@rpath)。在某些情况下,攻击者可以滥用此功能来运行任意可执行文件以执行代码和权限升级。
我运行了otool -L二进制文件来检查涉及哪些依赖项。事实证明,所有 pod(Cocaopod)和一些系统库都受到关注。
name @rpath/Alamofire.framework/Alamofire (offset 24)
name @rpath/libswiftCoreAudio.dylib (offset 24)
name @rpath/libswiftCoreData.dylib (offset 24)
name @rpath/libswiftCoreFoundation.dylib (offset 24)
Run Code Online (Sandbox Code Playgroud)
我想知道如何解决这个问题。Runpath Search Paths如果项目构建设置不包含 $(inherited),Cocoapods 会打印警告。
使用 @rpath 被认为有害吗?任何帮助/信息表示赞赏。