Android NDK-0.ndk-build的Android.mk和Android.mk简介

ndk-build是什么

ndk-build 文件是 Android NDK r4 中引入的一个 shell 脚本。其用途是调用正确的 NDK 构建脚本。可以用这个命令来生成.so文件。

ndk-build如何使用

当你想使用该命令将.cpp/.c文件生成.so文件,必须有具备以下几个条件

  1. 需有Android.mk文件,并且与对应的.cpp/.c文件在同一个大目录下,.cpp/.c文件可以在子目录,Android.mk中用相对路径标识。
  2. 需要有Application.mk文件,一般位于最上层大目录。

什么是Android.mk

参看谷歌官方的参考

变量:

LOCAL_PATH

Android.mk 文件必须首先定义 LOCAL_PATH 变量:

LOCAL_PATH := $(call my-dir)

my-dir 将返回当前目录(包含 Android.mk 文件本身的目录)的路径。

CLEAR_VARS

下一行声明 CLEAR_VARS 变量,其值由构建系统提供。

include $(CLEAR_VARS)

CLEAR_VARS 变量指向特殊 GNU Makefile,可为您清除许多 LOCAL_XXX 变量,例如 LOCAL_MODULELOCAL_SRC_FILESLOCAL_STATIC_LIBRARIES。 请注意,它不会清除 LOCAL_PATH。此变量必须保留其值,因为系统在单一 GNU Make 执行环境(其中所有变量都是全局的)中解析所有构建控制文件。 在描述每个模块之前,必须声明(重新声明)此变量。

LOCAL_MODULE

接下来,LOCAL_MODULE 变量将存储您要构建的模块的名称。请在应用中每个模块使用一个此变量。

LOCAL_MODULE := va++

每个模块名称必须唯一,且不含任何空格。构建系统在生成最终共享库文件时,会将正确的前缀和后缀自动添加到您分配给 LOCAL_MODULE 的名称。 例如,上述示例会导致生成一个名为 libva++.so 的库。

注:如果模块名称的开头已是 lib,则构建系统不会附加额外的前缀 lib;而是按原样采用模块名称,并添加 .so 扩展名。 因此,比如原来名为 libfoo.c 的源文件仍会生成名为 libfoo.so 的共享对象文件。 此行为是为了支持 Android 平台源文件从 Android.mk 文件生成的库;所有这些库的名称都以 lib 开头。

LOCAL_CFLAGS

LOCAL_CFLAGS此可选变量为构建系统设置在构建 C 和 C++ 源文件时要传递的编译器标志。 此功能对于指定额外的宏定义或编译选项可能很有用。

尽量不要更改 Android.mk 文件中的优化/调试级别。构建系统可使用 Application.mk 文件中的相关信息自动为您处理此设置。 这样允许构建系统生成在调试时使用的有用数据文件。

您现在可以使用 LOCAL_CPPFLAGS 只为 C++ 源文件指定标志

LOCAL_CFLAGS := -Wno-error=format-security -fpermissive -DLOG_TAG=\"VA++\"
LOCAL_CFLAGS += -fno-rtti -fno-exceptions

-Wno-error=format-security用于禁用指定的format-security类型Werror。
-fpermissive 允许编译一些不合格的代码,从错误降级为警告,兼容一些老的语法。
-DLOG_TAG=\"VA++\"定义一个LOG_TAG的宏。
-fno-rtti 禁用运行时类型信息。
-fno-exceptions 禁用异常机制。

LOCAL_C_INCLUDES

可以使用此可选变量指定相对于 NDK root 目录的路径列表,以便在编译所有源文件(C、C++ 和 Assembly)时添加到 include 搜索路径。 例如:

LOCAL_C_INCLUDES += $(MAIN_LOCAL_PATH)
LOCAL_C_INCLUDES += $(MAIN_LOCAL_PATH)/Foundation
LOCAL_C_INCLUDES += $(MAIN_LOCAL_PATH)/Jni

LOCAL_SRC_FILES

此变量包含构建系统用于生成模块的源文件列表。 只列出构建系统实际传递到编译器的文件,因为构建系统会自动计算所有关联的依赖关系。

LOCAL_SRC_FILES := Jni/VAJni.cpp \
				   Foundation/IOUniformer.cpp \
				   Foundation/VMPatch.cpp \
				   Foundation/SymbolFinder.cpp \
				   Foundation/Path.cpp \
				   Foundation/SandboxFs.cpp \
				   Substrate/hde64.c \
                   Substrate/SubstrateDebug.cpp \
                   Substrate/SubstrateHook.cpp \
                   Substrate/SubstratePosixMemory.cpp \

请注意,可以使用相对文件路径(指向 LOCAL_PATH)和绝对文件路径。

注:在构建文件中务必使用 Unix 样式的正斜杠 (/)。构建系统无法正确处理 Windows 样式的反斜杠 ()。

LOCAL_LDLIBS

此变量包含在构建共享库或可执行文件时要使用的其他链接器标志列表。 它可让您使用 -l 前缀传递特定系统库的名称, 以下依赖了liblog.solibatomic.so ,注意lib要省略。

LOCAL_LDLIBS := -llog -latomic

注: 如果为静态库定义此变量,构建系统会忽略它,并且 ndk-build 会显示一则警告。

LOCAL_STATIC_LIBRARIES

此变量用于存储当前模块依赖的静态库模块列表。如果当前模块是共享库或可执行文件,此变量将强制这些库链接到生成的二进制文件。如果当前模块是静态库,此变量只是指示,依赖当前模块的模块也会依赖列出的库。
以下表示它依赖于另一个libfb.a静态库。

LOCAL_STATIC_LIBRARIES := fb

BUILD_SHARED_LIBRARY

此变量指向的脚本用于收集您在 LOCAL_XXX 变量中提供的模块所有相关信息,以及确定如何从列出的源文件构建目标共享库。 请注意,使用此脚本要求您至少已为 LOCAL_MODULELOCAL_SRC_FILES 赋值,也就是应该先调用了include $(CLEAR_VARS)

include $(BUILD_SHARED_LIBRARY)

共享库变量导致构建系统生成具有 .so 扩展名的库文件。

BUILD_STATIC_LIBRARY

用于构建静态库的变体。构建系统不会将静态库复制到您的项目/软件包,但可能使用它们构建共享库(LOCAL_STATIC_LIBRARIES := fb),使用此变量的语法为:

include $(BUILD_STATIC_LIBRARY)

include xx/yy.mk

因为my-dir返回最后包含的 makefile 的路径,通常是当前 Android.mk 的目录。但是如果这样写:

LOCAL_PATH := $(call my-dir)

# ... declare one module

include $(LOCAL_PATH)/foo/`Android.mk`

LOCAL_PATH := $(call my-dir)
# ... declare another module

这里的问题在于,对 my-dir 的第二次调用将 LOCAL_PATH 定义为 $PATH/foo,而不是 $PATH,因为这是其最近 include 指向的位置。

Android.mk 文件中的任何其他内容后放置额外 include 可避免此问题

include $(MAIN_LOCAL_PATH)/fb/Android.mk

如果以这种方式构建文件不可行,请将第一个 my-dir 调用的值保存到另一个变量中。 例如:

MY_LOCAL_PATH := $(call my-dir)

LOCAL_PATH := $(MY_LOCAL_PATH)

# ... declare one module

include $(LOCAL_PATH)/foo/`Android.mk`

LOCAL_PATH := $(MY_LOCAL_PATH)

什么是Application.mk

参看谷歌官方的参考

变量:

APP_ABI

默认情况下,NDK 构建系统为 armeabi ABI 生成机器代码。您可以使用 APP_ABI 选择不同的 ABI。

APP_ABI := arm64-v8a

APP_PLATFORM

此变量包含目标 Android 平台的名称。例如,android-3 指定 Android 1.5 版本。 如需平台名称和对应 Android 系统映像的完整列表,请参阅 Android NDK 原生 API

APP_PLATFORM := android-14 // Android 4.0 到 4.0.2版本

APP_STL

默认情况下,NDK 构建系统为 Android 系统提供的最小 C++ 运行时库 (system/lib/libstdc++.so) 提供 C++ 标头。 此外,它随附您可以在自己的应用中使用或链接的替代 C++ 实现。请使用 APP_STL 选择其中一个

APP_STL := gnustl_static

gnustl_static其实就是LOCAL_MODULE 名字,指定了c++库用gnu的libstdc++.a静态库。

APP_OPTIM

将此可选变量定义为 releasedebug。在构建应用的模块时可使用它来更改优化级别。
发行模式是默认模式,可生成高度优化的二进制文件。调试模式会生成未优化的二进制文件,更容易调试。

在应用清单的 <application> 标记中声明 android:debuggable 将导致此变量默认使用 debug而非 release。 将 APP_OPTIM 设置为 release 可替换此默认值。

APP_OPTIM := release

其他全局定义

也可以在这里定义一些全局的宏

VA_ROOT          := $(call my-dir)
NDK_MODULE_PATH  := $(NDK_MODULE_PATH):$(VA_ROOT)

猜你喜欢

转载自blog.csdn.net/hgy413/article/details/86471848