学习NDK已经五天了,总刚开始的抵触,到如今的慢慢适应,一直觉得想要今后想要从事NDk开发的话基础需要打好,不然以后会花数倍的代价来弥补。
const char*ptr:
StackOverFlowError
JVM会限定栈的深度,一旦超过该深度就会报错,几种常见的场景.
1 Layout布局嵌套过深,导致栈内存溢出,建议控制在5层以下.
2 注意线程并发的数量,每个线程都会申请独立的栈空间,不加控制可能几百条线程一起把JVM限定的栈空间耗完。
3 查看错误堆栈是否存在代码嵌套地柜调用.
ndk目录
配置externalNativeBuild{
ndkBuild{
//这里是path mk文件
}
}
ndkBuild Android.mk hello-jni.c libTest.so 这里是ndk的文件。
编译 hello-jni模块 需要链接Test模块。
Test模块是一个预编译库模块,
LOCAL_SHARED
NDK depends-md 这个工具的作用就是能够让我们查看这个so的依赖.
Android手机没有以盘符为路径的路径。
6.0 Android 如果load 一个动态库,需要将这个动态库的依赖的其他的动态库也加载进来。不然就会报错。
6.0以上 System.loadLibrary会为我们自动的添加动态库的library.
静态库和动态库的区别:
动态库作为编译的库 会包含2个so.
静态库会把库里面的函数整个打包进来。(只会加载使用到的so库。
动态库:不管有没有使用会把整个apk都加载进来。
app jar包中有我们需要的的a.java文件。
使用到了app.java:
如果是动态库的话会把整个jar包给打包进来。
所以我们推荐打包静态库而非动态库。
但是动态库方便你使用,静态库需要自己手动的配置很多的信息。
6.0以上使用静态库会有问题。---mk.
所以这里开始我们的CMake库就登场了。
cooks2d目录 android
mk
LOCAL_C_INCLUDES 编译时查找头文件的路径。
-i 头文件的查找路径
引入一个静态库作为当前编译源文件的依赖。
---以上是mkfile
cpp flag 会交给编译器的参数
如何将mk移植到cmake文件中。
CMAKE (为了解决mk编译麻烦而创建的一个工具)
CMake不生成so,生成的是mkfile,由mkfile去生成so.
sdk中的nijia.so工具,AS当中生成so.有nijia生成so。
cmakelists.txt中第一句话需要指定版本。
- 指定最小版本号
cmake_minimum_required(VERSION 3.8)
2.编译hello.jni.c
//变量名 最终会生成的so的名字
//SHARED 动态库
//STATIC静态库
add_library(hello-jni SHARED hello-jni.c)
注意!静态的导入的时候 需要设置导入的路径,不然直接使用
STATIC_IMPORTED会出现找不到的情况。
//所以需要导入该路径的属性
set_target_properties(Test PROPERTIES IMPORTED_LOCATION libTest.a)
%CMAKE_SOURCE_DIR
动态库需要放入到jniLibs/arm-v7目录下不然会找不到。
动态库会找路径去找so,d://xxx.路径下去找,但是CMAKE使用了另外一种方式去引入动态库.
set(CMAKE_C_FLAGS)
如果使用了c++就用CMAKE_CXX_FLAGS -L{ANDROID_ABI
所以我们得出结论
CMAKE 6.0以上引入动态库 加入路径,相当语自己指定路径,这样就不会使用默认的d;//test.so这样的路径了,详见老师的笔记中。
find_library(${log-lib} log)
find_library 就是去查找log库,如果查找到了就会把liblog.so的绝对路径赋值给log.
从哪里去找log.so?
会根据Sdk的配置去NDK下面的platform下的liblog.so下去寻找。
message("log_lib")
file(GLOB src/main/cmake.c src/main/cmake.......cpp)目录下引入文件。
网友评论