從網上查找知道RPATH的優先級高於LD_LIBRARY_PATH
那LD_LIBARY_PATH中的多個路徑存在同名的so文件的時候bin會選擇哪一個?
用兩個so和一個bin做實驗驗證下上面兩個問題
實驗環境gcc 5.4 ubuntu 16
文件目錄結構
a.c b.c mai.c build.sh start.sh ./lib ./lib/deps
文件內容如下
a.c
#include <stdio.h>
void test_func(void)
{
printf("this is a.so test func\n");
}
b.c
#include <stdio.h>
void test_func(void)
{
printf("this is b.so test func\n");
}
main.c
#include <stdio.h>
extern void test_func(void);
int main(void)
{
test_func();
return 1;
}
build.sh
#!/bin/sh
gcc ./a.c -fPIC -shared -o libtest.so
cp ./libtest.so ./lib
gcc ./b.c -fPIC -shared -o libtest.so
cp ./libtest.so ./lib/deps
rm -rf libtest.so
gcc main.c -L./lib -ltest -o test
start.sh
#!/bin/sh
export LD_LIBRARY_PATH=./lib:./lib/deps
./test
將start.sh 的LD_LIBRARY_PATH 中lib和lib/deps的順序變換可以得到不同的輸出結果並可以得知,elf文件運行時在LD_LIBRARY_PATH中查找依賴so文件時會加載放在前面位置的so文件
如果有指定-rpath的情況下結果,build 腳本修改如下
build.sh
#!/bin/sh
gcc ./a.c -fPIC -shared -o libtest.so
cp ./libtest.so ./lib
gcc ./b.c -fPIC -shared -o libtest.so
cp ./libtest.so ./lib/deps
rm -rf libtest.so
gcc main.c -L./lib -ltest -Wl,-rpath=/home/faun/so_path/lib -o test
可以用readelf -d test 查看rpath 段的內容
faun@faun-TM1701:~/proj/so_path$ readelf -d test
Dynamic section at offset 0xe08 contains 26 entries:
標記 類型 名稱/值
0x0000000000000001 (NEEDED) 共享庫:[libtest.so]
0x0000000000000001 (NEEDED) 共享庫:[libc.so.6]
0x000000000000000f (RPATH) Library rpath: [/home/faun/so_path/lib]
0x000000000000000c (INIT) 0x400548
lib目錄中放的是a lib/deps中放的是b
添加了rpath後 ./start.sh的執行結果依然是根據LD_LIBRARY_PATH中的靠前的路徑
最終結論:
同名的so文件同時出現在LD_LIBRARY_PATH的不同路徑時候靠前的PATH中的so會被優先加載
即使定義了rpath,elf 執行時候會優先加載LD_LIBRARY_PATH路徑中的so