/*****************************************
FileName: main2.c
Description: test static/dynamic library
Author: HCJ
Date : 2005-5-7
******************************************/
#include<stdio.h>
#include<dlfcn.h>
int main(int argc, char* argv[])
{
//define function pointor
int (*pStrlenFun)(char* pStr); //声明对应的函数的函数指针
int (*pStrnlenFun)(char* pStr, int ulMaxLen);
char str[] = {"hello world"};
unsigned long ulLength = 0;
void *pdlHandle;
char *pszErr;
pdlHandle = dlopen("./libstr.so", RTLD_LAZY); //加载链接库/libstr.so
if(!pdlHandle)
{
printf("Failed load library\n");
}
pszErr = dlerror();
if(pszErr != NULL)
{
printf("%s\n", pszErr);
return 0;
}
//get function from lib
pStrlenFun = dlsym(pdlHandle, "Strlen"); //获取函数的地址
pszErr = dlerror();
if(pszErr != NULL)
{
printf("%s\n", pszErr);
return 0;
}
pStrnlenFun = dlsym(pdlHandle, "StrNlen");
pszErr = dlerror();
if(pszErr != NULL)
{
printf("%s\n", pszErr);
return 0;
}
printf("The string is : %s\n", str);
ulLength = pStrlenFun(str); //调用相关的函数
printf("The string length is : %d(use Strlen)\n", ulLength);
ulLength = pStrnlenFun(str, 10);
printf("The string length is : %d(use StrNlen)\n", ulLength);
dlclose(pdlHandle);
return 0;
}
用gcc编译对应的源文件生成可执行文件,-ldl选项,表示生成的对象模块需要使用共享库。执行对应得文件同样可以得到正确的结果。
相关函数的说明如下:
(1)dlopen()
第一个参数:指定共享库的名称,将会在下面位置查找指定的共享库。
-环境变量LD_LIBRARY_PATH列出的用分号间隔的所有目录。
-文件/etc/ld.so.cache中找到的库的列表,用ldconfig维护。
-目录usr/lib。
-目录/lib。
-当前目录。
第二个参数:指定如何打开共享库。
-RTLD_NOW:将共享库中的所有函数加载到内存
-RTLD_LAZY:会推后共享库中的函数的加载操作,直到调用dlsym()时方加载某函数
(2)dlsym()
调用dlsym时,利用dlopen()返回的共享库的phandle以及函数名称作为参数,返回要加载函数的入口地址。
(3)dlerror()
该函数用于检查调用共享库的相关函数出现的错误。
这样我们就用简单的例子说明了在Linux下静态/动态库的创建和使用。