the different linkage

  链接方式的区别


2017-08-21



	
	
	
		
	1. 关于链接方式的区别1.0.1. 动态库的调用链接方式1.0.2. 两种调用方式
	
	
	关于链接方式的区别动态库的调用链接方式

动态库调用方式可分为两种:

显式调用
隐式调用

两种调用方式
显式调用
在程序中直接通过动态库装载的方式,对程序中定义的 [函数指针]进行加载和赋值。
下面是用例:
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849//定义函数指针 以及变量void functionLib; / Handle to shared lib file */char dlError; / Pointer to error string *///magint (*NDK_MagOpen)(void);int (*NDK_MagClose)(void);int (*NDK_MagSwiped)(uchar * psSwiped);int (*NDK_MagReadNormal)(char *pszTk1, char *pszTk2, char *pszTk3, int *pnErrorCode);// … 省略N行 …// onload.c// 定义了一个加载宏#define DLSYM(lib, foo) { \ dlError = (char )dlerror(); \ foo = dlsym( lib , #foo); \ if( dlError || NULL == foo ){ \ foo = NULL; \ nRet -= 1; \ LOGI(“dlsym “#foo” fail:%s,Addr:%x,nRet:%d.”, dlError, (int)foo, nRet); \ } \ else{ \ LOGI(“dlsym “#foo” succ. Addr:%x.”, (int)foo); \ } \ }; //——- 通过显示加载方式加载库文件 ——————– int nRet = 0; / return codes */ // libnl_ndk.so // libnlposapi.so functionLib = dlopen(“/system/lib/libabcd.so”,RTLD_LAZY); dlError = (char *)dlerror(); LOGI(“dlopen libnlposapi.so error:%s”, dlError); if( functionLib == NULL ) { return (-1000); } //mag DLSYM(functionLib, NDK_MagOpen); DLSYM(functionLib, NDK_MagClose); DLSYM(functionLib, NDK_MagSwiped); DLSYM(functionLib, NDK_MagReadNormal); // … 省略N行 …
这时候 在mk文件中可以不需要链接这个库(libabcd.so)就可以调用这个库里面的函数。
像这样:
int ret= NDK_MagOpen();
这时NDK头文件中也将函数声明定义为函数指针的方式:
int (*NDK_MagOpen)();

隐式调用
即通过在mk文件中显示指定需要调用链接的函数库的名称,然后在程序运行的过程中由os系统中的装载器以及链接器来完成函数的装载和链接过程。
如果一个函数定义在libabcd.so中时,我们需要调用它,就要在Android.mk文件中显示指定调用链接函数库名称:
LOCAL_LDLIBS += labcd
然后在NDK头文件中声明为函数调用方式(注意区别前面的函数指针的什么方式):
int NDK_MagOpen();
然后调用方式同函数指针的方式:
int ret= NDK_MagOpen();

notes

notes