库
来源:互联网 发布:vb.net 高级 编辑:程序博客网 时间:2024/04/28 08:37
library_name.major_num.minor_num.patch_num
_g是调试库,增加对库的调试功能。
_p代码剖析库,增加复杂的代码剖析和性能分析。
命令:
nm [options] file
列出保存在file中的符号。
-c|--demangle将符号名转换为用户级的名字。在让c++函数名可读方面特别有用。
-s|--print-armap当用于存档(.a)文件时,输出把符号名映射到定义该符号的模块或成员名的索引
-u|--undefined-only只显示未定义的符号--在被检查的文件外部定义的符号。
-l|--line-numbers使用调试信息输出定义每个符号的行号,或者未定义符号的重定位项。
ar {dmpqrtx} [member] archive files ...
用于操作高度结构化的存档archive文件。最常用来创建静态库--包含一个或多个目标文件,预编译格式的例程的目标文件称为成员。
ldd [options] file
列出为使程序正常运行所需要的共享库。
ldconfig [options] file
决定位于目录/usr/lib和/lib下的共享库所需的运行的链接,这些链接在命令行上的libs指定并被保存在/etc/ld.so.conf中
动态链接器/加载器ld.so,使用
$LD_LIBRARY_PATH = /etc/ld.so.config
$LD_PRELOAD = /etc/ld.so.preload
----------------------------------
创建一个静态库
编译为目标文件。
gcc -c liberr.c -o liberr.o
使用ar创建一个存档文件。
ar rcs liberr.a liberr.o
调用liberr.a
包含头文件
#include "liberr.h"
编译命令
gcc errtest.c -o errtest -static -L. -lerr
如果没使用-static,gcc将使用动态库创建errtest.c
-lerr告诉gcc在当前命令下查找库文件liberr
-L{dirname}添加库文件搜索路径
-l选项使得链接程序使用指定的库函数中目标代码,也就是本例中的liberr.a,函数库命名为lib是约定。
nm errtest显示二进制文件中的符号。
---------------------------------------
创建一个共享库
应用程序链接到so名字。ldconfi工具创建一个从实际库到so名字的符号链接。并且把这些信息保存在缓冲文件/etc/ld.so.cache中。在运行时,ld.so读取该缓冲,找到所需的so名字,把实际的库加载到内存中,并且把应用程序中的函数调用链接到加载库中合适的符号上。
创建过程:
编译文件
gcc -fPIC -g -c liberr.c -o liberr.o
-fPIC产生与位置无关的代码并能被加载到任何地址。
链接库
gcc -g -shared -wl, -soname, liberr.so -o liberr.so.1.0.0 liberr.o -lc
-wl把参数传递给链接器ld。
由于不想把该库作为系统库安装到/usr/lib或/usr上,所以要建立必须的符号链接,一个用于soname:
ln -s liberr.so.1.0.0 liberr.so.1
另一个链接程序在使用-lerr链接到liberr时使用的
ln -s liberr.so.1.0.0 liberr.so
链接库
gcc -g errtest.c -o errtest -L. -lerr
执行程序,告诉ld.so在哪里找到这个共享库
LD_LIBRARY_PATH=$(pwd) ./errtest
或者
把库路径添加到/etc/ld.so.config,然后运行ldconfig更新/etc/ld.so.cache
或者
把库放到/usr/lib,建立一个到soname的符号链接,然后运行ldconfig更新/etc/ld.so.cache
------------------------------------------
动态加载的共享对象
加载共享对象
void *dlopen(const char* filename, int flag);
使用共享对象
void *dlsym(void *handle, char* symbol);
在加载的对象handle中搜索在symbol中命名的符号或函数。
handle是dlopen返回的句柄。
函数dlsym返回指向符号的空指针,若发生错误则返回NULL.
const char*dlerror(void);
如果任何函数出错,则函数dlerror返回一个描述错误的字符串,再把错误字符串置为NULL。
函数dlerror返回描述最近发生错误的字符串,在没有错误时返回NULL。
卸载共享对象
int dlclose(void* handle);
只有dlclose的次数等于 dlopen时,所占用的资源才会返回给操作系统。
编译命令
gcc -g -Wall dltest.c -o dltest -ldl