Kam*_*ath 14 c linux shared-libraries
我需要在程序的执行周期中使用不同的动态库.看着dlfcn.h
我认为这是可能的.我承认没有阅读很多关于动态库加载的文献.
好的,这就是我做的 -
一切都很好,直到这里.
有人可以解释为什么这个分段错误?
我注意到即使我删除libdynamicTest.so.1程序仍然执行,安静奇怪.
SysTrace(("opening dynamic library"));
handle = dlopen("libdynamicTest.so.1",RTLD_LAZY);
fn = dlsym (handle,"dylib_print_msg");
SysTrace(("Using dynamic library"));
if(!fn)
{
printf("unknown dylib_print_msg..!!\n");
}
else
{
(*fn)();
}
ret = dlclose(handle);
SysTrace(("closed dynamic library status = [%s]", (ret==0?"OK":"NOK")));
Run Code Online (Sandbox Code Playgroud)
PS我不是试图修改任何现有程序的行为,也不构成任何威胁.我正在进行可行性检查以将集成测试作为共享库运行.
编辑
我尝试使用gdb,以下是堆栈跟踪,当发生故障时.
Program received signal SIGSEGV, Segmentation fault.
0x0000003e92408b7b in check_match.8509 () from /lib64/ld-linux-x86-64.so.2
#0 0x0000003e92408b7b in check_match.8509 ()
from /lib64/ld-linux-x86-64.so.2
#1 0x0000003e92409024 in do_lookup_x () from /lib64/ld-linux-x86-64.so.2
#2 0x0000003e92409222 in _dl_lookup_symbol_x ()
from /lib64/ld-linux-x86-64.so.2
#3 0x0000003e92908f14 in do_sym () from /lib64/libc.so.6
#4 0x0000003e93001104 in dlsym_doit () from /lib64/libdl.so.2
#5 0x0000003e9240ced6 in _dl_catch_error ()
from /lib64/ld-linux-x86-64.so.2
#6 0x0000003e9300150d in _dlerror_run () from /lib64/libdl.so.2
#7 0x0000003e930010ba in dlsym () from /lib64/libdl.so.2
Run Code Online (Sandbox Code Playgroud)
编辑
在svn checkout上共享的代码库 http://subversion.assembla.com/svn/dynamic_libso
编辑: - 添加日志LD_DEBUG =全部
32564: binding file ./test_agent [0] to /lib64/libc.so.6 [0]: normal symbol `__libc_start_main' [GLIBC_2.2.5]
32564:
32564: initialize program: ./test_agent
32564:
32564:
32564: transferring control: ./test_agent
32564:
32564: symbol=printf; lookup in file=./test_agent [0]
32564: symbol=printf; lookup in file=/lib64/libdl.so.2 [0]
32564: symbol=printf; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: symbol=printf; lookup in file=/lib64/libc.so.6 [0]
32564: binding file ./test_agent [0] to /lib64/libc.so.6 [0]: normal symbol `printf' [GLIBC_2.2.5]
32564: symbol=putchar; lookup in file=./test_agent [0]
32564: symbol=putchar; lookup in file=/lib64/libdl.so.2 [0]
32564: symbol=putchar; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: symbol=putchar; lookup in file=/lib64/libc.so.6 [0]
32564: binding file ./test_agent [0] to /lib64/libc.so.6 [0]: normal symbol `putchar' [GLIBC_2.2.5]
-hello.c main():20 Msg : hello world ..!!
-hello.c main():24 Msg : opening dynamic library
32564: symbol=dlopen; lookup in file=./test_agent [0]
32564: symbol=dlopen; lookup in file=/lib64/libdl.so.2 [0]
32564: binding file ./test_agent [0] to /lib64/libdl.so.2 [0]: normal symbol `dlopen' [GLIBC_2.2.5]
32564: opening file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]; direct_opencount=1
32564:
32564: symbol=dlerror; lookup in file=./test_agent [0]
32564: symbol=dlerror; lookup in file=/lib64/libdl.so.2 [0]
32564: binding file ./test_agent [0] to /lib64/libdl.so.2 [0]: normal symbol `dlerror' [GLIBC_2.2.5]
-hello.c main():26 Msg : Opened dynamic library handle = [a16d9000]
32564: symbol=dlsym; lookup in file=./test_agent [0]
32564: symbol=dlsym; lookup in file=/lib64/libdl.so.2 [0]
32564: binding file ./test_agent [0] to /lib64/libdl.so.2 [0]: normal symbol `dlsym' [GLIBC_2.2.5]
32564: symbol=_dl_sym; lookup in file=./test_agent [0]
32564: symbol=_dl_sym; lookup in file=/lib64/libdl.so.2 [0]
32564: symbol=_dl_sym; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: symbol=_dl_sym; lookup in file=/lib64/libc.so.6 [0]
32564: binding file /lib64/libdl.so.2 [0] to /lib64/libc.so.6 [0]: normal symbol `_dl_sym' [GLIBC_PRIVATE]
32564: symbol=solib_print_msg; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: binding file /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0] to /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]: normal symbol `solib_print_msg'
-hello.c main():28 Msg : Using dynamic library
32564: symbol=printf; lookup in file=./test_agent [0]
32564: symbol=printf; lookup in file=/lib64/libdl.so.2 [0]
32564: symbol=printf; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: symbol=printf; lookup in file=/lib64/libc.so.6 [0]
32564: binding file /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0] to /lib64/libc.so.6 [0]: normal symbol `printf' [GLIBC_2.2.5]
32564: symbol=putchar; lookup in file=./test_agent [0]
32564: symbol=putchar; lookup in file=/lib64/libdl.so.2 [0]
32564: symbol=putchar; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: symbol=putchar; lookup in file=/lib64/libc.so.6 [0]
32564: binding file /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0] to /lib64/libc.so.6 [0]: normal symbol `putchar' [GLIBC_2.2.5]
-dynamic.c solib_print_msg():9 Msg : nice nice..!!
32564: symbol=dlclose; lookup in file=./test_agent [0]
32564: symbol=dlclose; lookup in file=/lib64/libdl.so.2 [0]
32564: binding file ./test_agent [0] to /lib64/libdl.so.2 [0]: normal symbol `dlclose' [GLIBC_2.2.5]
32564:
32564: closing file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1; direct_opencount=0
-hello.c main():40 Msg : closed dynamic library status = [OK]
-hello.c main():24 Msg : opening dynamic library
32564: opening file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]; direct_opencount=1
32564:
-hello.c main():26 Msg : Opened dynamic library handle = [0]
32564: symbol=solib_print_msg; lookup in file=/user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]
32564: binding file /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0] to /user/skm/coding/fTest/approach/dynamic_library/gravity/contribs/libs/libdynamicTest.so.1 [0]: normal symbol `solib_print_msg'
-hello.c main():28 Msg : Using dynamic library
Segmentation fault
Run Code Online (Sandbox Code Playgroud)
Emp*_*ian 10
来自"man dlclose":
The function dlclose() decrements the reference count on the dynamic
library handle handle. If the reference count drops to zero and
no other loaded libraries use symbols in it, then the dynamic library
is unloaded.
Run Code Online (Sandbox Code Playgroud)
我猜你正在运行"没有其他加载的库使用符号"部分.
要调试,运行程序LD_DEBUG=bindings
,并查找以下消息:
binding file <some.so> [0] to libdynamicTest.so.1 [0]: normal symbol `<symbol>'
Run Code Online (Sandbox Code Playgroud)
更新:
你有几个错误:
您链接test_agent
对libdynamic.so.1
直接:
cc -o test_agent -L. ...-ldl build/test_agent/hello.o libdynamic.so.1
一旦你做到了这一点,你不能再指望这个库被不断卸载.
通过做这个:
*((int *)handle) = 0;
你实际上正在破坏动态加载器的状态,这会导致随后dlsym
给你伪造的地址,这会导致SIGSEGV
你尝试使用它时.
一旦你解决问题#2,你的程序将不会再崩溃,尽管它仍然不会卸载库.要实际卸载库,您还需要解决问题#1.
如果您首先解决问题#1,那么问题#2将不再破坏动态加载程序.它会破坏堆,你可以用Valgrind轻松地观察它.