文章目录
-
- [一、ndk-build 构建系统](#一、ndk-build 构建系统)
-
- [1.1 什么是 ndk-build 构建系统](#1.1 什么是 ndk-build 构建系统)
- [1.2 核心配置文件](#1.2 核心配置文件)
-
- [1.2.1 Android.mk - 模块级配置](#1.2.1 Android.mk - 模块级配置)
- [1.2.2 Application.mk - 项目级配置](#1.2.2 Application.mk - 项目级配置)
- [1.3 ndk-build 构建流程](#1.3 ndk-build 构建流程)
- [1.4 ndk-build 最佳实践](#1.4 ndk-build 最佳实践)
- [二、CMake 构建系统](#二、CMake 构建系统)
-
- [2.1 什么是 CMake](#2.1 什么是 CMake)
- [2.2 CMake 构建流程](#2.2 CMake 构建流程)
- [2.3 CMakeLists.txt 配置示例](#2.3 CMakeLists.txt 配置示例)
- 总结
- 参考资料
一、ndk-build 构建系统
1.1 什么是 ndk-build 构建系统
ndk-build 是 Android NDK 的传统构建系统,基于 GNU Make 构建工具。它通过解析特定配置文件来编译原生代码,专为 Android 平台设计。
在使用过程中,通过 NDK 安装目录中的 ndk-build 脚本 驱动 GNU Make,读取 jni/ 下的 Application.mk 以及各处的 Android.mk 来编译项目。
1.2 核心配置文件
1.2.1 Android.mk - 模块级配置
Android.mk 文件位于项目 jni/ 目录的子目录中,用于向构建系统描述源文件和共享库。它实际上是一个微小的 GNU Makefile 片段,构建系统会将其解析一次或多次。Android.mk 文件用于定义 Application.mk、构建系统和环境变量所未定义的项目级设置。它还可替换特定模块的项目级设置。
makefile
# 示例:定义原生共享库模块
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := native-lib
LOCAL_SRC_FILES := native-lib.cpp
LOCAL_LDLIBS := -llog
include $(BUILD_SHARED_LIBRARY)
1.2.2 Application.mk - 项目级配置
Application.mk 定义项目全局设置,默认位于应用项目目录中的 jni/Application.mk 下。Application.mk配置目标ABI、标准库、最低 API 平台、STL、NDK 工具链与优化级别等
makefile
# 示例:支持多种ABI架构
APP_ABI := armeabi-v7a arm64-v8a x86 x86_64
APP_STL := c++_static
APP_PLATFORM := android-24
1.3 ndk-build 构建流程
Android.mk 是 Makefile 片段,由 NDK 顶层 Makefile include ,在同一次 make 中与内置规则一起展开,由 GNU Make 直接完成编译链接。这与 CMake 的典型两阶段(先配置生成 Ninja 等构建文件,再执行 Ninja)不同。具体流程如下所示:
源代码文件
↓
Android.mk + Application.mk
↓
ndk-build 解析配置
↓
生成完整的 GNU Makefile
↓
GNU Make 驱动构建过程
↓
编译 → 汇编 → 链接
↓
生成目标库文件 (lib*.so/lib*.a)
注意:ndk-build 会为每个 ABI 独立执行一套完整的构建流程:
# Application.mk 中指定多个 ABI
APP_ABI := armeabi-v7a arm64-v8a x86 x86_64
# 构建系统执行流程:
1. 加载配置,为 armeabi-v7a 解析 Android.mk
2. 生成 armeabi-v7a 专用的中间文件
3. 完成 armeabi-v7a 构建
4. 重复 1--3 步处理其他 ABI
1.4 ndk-build 最佳实践
# 清晰的项目结构
jni/
├── Android.mk
├── Application.mk
├── common.mk (通用配置)
├── module1/
│ ├── Android.mk
│ └── src/
└── module2/
├── Android.mk
└── src/
# 模块化配置
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS) # 清除之前变量
include $(LOCAL_PATH)/../common.mk # 包含通用配置
二、CMake 构建系统
2.1 什么是 CMake
CMake 是跨平台的开源构建系统生成器,Android Studio 从 2.2 版本起将其作为 NDK 构建的推荐方式。CMake 不直接编译源码,而是生成 Ninja 等构建工具所需的构建脚本,再由后者执行实际编译与链接。
2.2 CMake 构建流程
CMake 在 Android NDK 场景下的大致流程如下:
源代码文件
↓
CMakeLists.txt (用户配置)
↓
CMake + Android Toolchain
↓
生成 Ninja 构建文件 (build.ninja)
↓
Ninja 执行实际构建任务
↓
编译 → 链接 → 打包
↓
生成最终原生库文件
CMake 只需一次配置即可为所有目标 ABI 生成构建规则,相比 ndk-build 通常更高效。
2.3 CMakeLists.txt 配置示例
cmake
# 最低 CMake 版本要求
cmake_minimum_required(VERSION 3.18.1)
# 项目定义
project("native-lib")
# 创建共享库
add_library(
native-lib # 库名称
SHARED # 共享库类型
native-lib.cpp # 源文件
)
# 链接系统库
target_link_libraries(
native-lib
log # Android日志库
android # Android NDK库
)
# 包含目录
target_include_directories(
native-lib
PRIVATE
include
)
# 编译定义
target_compile_definitions(
native-lib
PRIVATE
DEBUG=1
)
总结
CMake 是更现代、更跨平台的解决方案,而 ndk-build 是 Android 特定的传统方式。Google 现在推荐使用 CMake 进行新的 NDK 开发。
| 功能 | Android.mk | CMakeLists.txt |
|---|---|---|
| 定义模块 | LOCAL_MODULE := native-lib |
add_library(native-lib SHARED ...) |
| 源文件 | LOCAL_SRC_FILES := a.cpp b.cpp |
add_library(native-lib a.cpp b.cpp) |
| 包含目录 | LOCAL_C_INCLUDES := $(LOCAL_PATH)/include |
target_include_directories(native-lib PRIVATE include) |
| 链接库 | LOCAL_LDLIBS := -llog -landroid |
target_link_libraries(native-lib log android) |
| 编译标志 | LOCAL_CFLAGS := -DDEBUG=1 |
target_compile_definitions(native-lib PRIVATE DEBUG=1) |