① 如何将debug版本的so库变成release版本
由于Smart_Gis安卓客户端的需要,所以需要把gdal_2.3.1库编译成安卓平台Arm64_v8a版本的.so库。由于要求是android NDK版本 12以上,Android API 21以上的支持。
所以在本次编译过程中全部需要使用64位的操作系统,NDK及编译器,编译环境为 操作系统:Ubuntu 16.04 LTS,安卓NDK版本:android-ndk-r14b,geos, proj。
1,最近遇到了之前编译的geos, proj, skia, gdal库都为debug版本,本人也没有特意的去验证,但是由于项目上线发布的原因,需要将所有的依赖的库发布成release版本的,一来可以增加库的稳定性,二来可以减小体积。
2,由于 gdal 库在编译成release版本的过程中可以参考我的gdal库安卓平台编译这篇文章,并在Application.mk文件里面增加 APP_OPTIM := release 然后 ndk-build命令进行编译就行了,如何验证生成的库是不是debug版本的呢?
在库目录下执行 readelf -S + 文件名 ,在打印出的信息中如果能查看到有debug字符即是debug版本。
3,到这一步我们需要找到我们打开我们编译的工具链的位置,找到strip这个可执行程序,比如说 GCC存储目录或者本人的Android 交叉编译工具链的位置。然后找到存储.so库的目录下并复制当前目录加上需要裁剪的库名到工具链strip存放目录下,
如下图所示并回车。
4,再次查看SO库并会发现该库的体积缩小了很多,并使用readelf -S + 库名打印出来的信息没有debug字符。
② C++或者VB编译dll或者lib的时候,如何加入版本号
打开这个DLL工程在菜单里选
Insert——Resource——Version
然后编辑你的Version就行了
=========================
我猜你的是static library吧?静态库是不能加入版本号的
========================
LIB有两种的,一种是由DLL导出的LIB库,一种是static lib;前者不包括任何操作代码,只有一些符号信息;后面是包括代码的LIB;前者的LIB有可能是带的版本号的,后者是没有版本号的;
以上纯粹个人理解
③ linux静态库怎么编译
linux库有动态与静态两种,动态通常用.so为后缀,静态用.a为后缀。例如:libhello.so
libhello.a
为了在同一系统中使用不同版本的库,可以在库文件名后加上版本号为后缀,例如:
libhello.so.1.0,由于程序连接默认以.so为文件后缀名。所以为了使用这些库,通常使用建立符号连接的方式。
ln
-s
libhello.so.1.0
libhello.so.1
ln
-s
libhello.so.1
libhello.so
动态库和静态库的区别:
当要使用静态的程序库时,连接器会找出程序所需的函数,然后将它们拷贝到执行文件,由于这种拷贝是完整的,所以一旦连接成功,静态程序库也就不再需要了。然而,对动态库而言,就不是这样。动态库会在执行程序内留下一个标记‘指明当程序执行时,首先必须载入这个库。由于动态库节省空间,linux下进行连接的缺省操作是首先连接动态库,也就是说,如果同时存在静态和动态库,不特别指定的话,将与动态库相连接。
两种库的编译产生方法:
第一步要把源代码编绎成目标代码。以下面的代码hello.c为例,生成hello库:
/*
hello.c
*/
#include
void
sayhello()
{
printf("hello,world\n");
}
用gcc编绎该文件,在编绎时可以使用任何全法的编绎参数,例如-g加入调试代码等:
gcc
-c
hello.c
-o
hello.o
1.连接成静态库
连接成静态库使用ar命令,其实ar是archive的意思
$ar
cqs
libhello.a
hello.o
2.连接成动态库
生成动态库用gcc来完成,由于可能存在多个版本,因此通常指定版本号:
$gcc
-shared
-wl,-soname,libhello.so.1
-o
libhello.so.1.0
hello.o
另外再建立两个符号连接:
$ln
-s
libhello.so.1.0
libhello.so.1
$ln
-s
libhello.so.1
libhello.so
这样一个libhello的动态连接库就生成了。最重要的是传gcc
-shared
参数使其生成是动态库而不是普通执行程序。
-wl
表示后面的参数也就是-soname,libhello.so.1直接传给连接器ld进行处理。实际上,每一个库都有一个soname,当连接器发现它正在查找的程序库中有这样一个名称,连接器便会将soname嵌入连结中的二进制文件内,而不是它正在运行的实际文件名,在程序执行期间,程序会查找拥有
soname名字的文件,%b