程序员自我修养-笔记(六)

133 阅读2分钟

共享库的组织

共享库的兼容

由于共享库的优点,许多程序都采用了共享库作为通用的库,而减少了静态库的使用。系统中,就会存在许多的共享库, 各个版本不一。在编译的时候,会在可执行文件的.dynamic段中写入程序依赖的动态库的SO_NAME。SO_NAME是一个类似libname.so.3的字符串,表示依赖名称为name的动态库, 动态库的版本为3.x.x。对于linux,动态库有其命名的规则,为libname.so.3.1.2。版本号的定义遵循semver格式。在linux中,还会存在一个libname.so.3的软链接,指向name对应的主版本为3的最新的版本文件,这样就解决了版本的兼容问题。

gcc -o main -lname // -lname 表示需要链接libname.so.a.b.c, 具体的版本由编译环境决定

但是这个方案无法解决依赖的次版本比实际运行次版本高的问题。次版本号只保证向后兼容, 不保证向前兼容, 可能出现某些接口找不到的问题,需要注意。

共享库的查找路径

程序依赖的共享库会被保存到.dynamic段中, 然后加载的时候由动态链接器进行加载,如果保存的是绝对路径,直接按路径加载;如果是相对路径或者纯文件名,则按/lib, /usr/lib, 和/etc/ld.so.conf配置的路径查找。还有基于ldconfig的缓存优先查找。

还可以基于环境变量LD_LIBRARY_PATH设置优先查找路径

LD_LIBRARY_PATH=/home/lib /bin/ld  ./exec_file

查看共享库的查找过程可以设置环境变量 LD_DEBUG, 然后执行程序 会有具体的信息输出。

LD_DEBUG=files  ./exec_file

行动,才不会被动!

欢迎关注个人公众号 微信 -> 搜索 -> fishmwei

github博客: fishmwei.github.io/