This document explains the
Application.mk build file, which describes the
native modules that your app requires. A module can be a static library, a shared library,
or an executable.
Application.mkfile is really a tiny GNU Makefile fragment that defines several variables for compilation. It usually resides under
$PROJECTpoints to your application's project directory. Another alternative is to place it under a sub-directory of the top-level
$NDK/apps/directory. For example:
<myapp> is a short name used to describe your app to the NDK build system. It
doesn't actually go into your generated shared libraries or your final packages.
This variable stores the absolute path to your app's project-root directory. The build system uses this information to place stripped-down versions of the generated JNI shared libraries into a specific location known to the APK-generating tools.
If you place your
Application.mk file under
$NDK/apps/<myapp>/, you must
define this variable. If you place it under
$PROJECT/jni/, it is optional.
If this variable is defined, it tells
ndk-build to build only the corresponding
modules and those that they depend on. It must be a space-separated list of module names as they
appear in the
LOCAL_MODULE definition of
If the variable is undefined,
ndk-build looks for the list of all installable
top-level modules, i.e. those listed by your
Android.mk file and any file it includes
directly. Imported modules are not top-level though.
An installable module is either a shared library or executable, which will generate a file in
If the variable is undefined, and there are no installable top-level modules in your project,
ndk-build builds all top-level static libraries and their dependencies instead.
These libraries are placed at the usual location under
Define this optional variable as either
debug. You use it to
alter the optimization level when building your application's modules.
Release mode is the default, and generates highly optimized binaries. Debug mode generates unoptimized binaries that are much easier to debug.
Note that you can debug either release or debug binaries. Release binaries, however, provide less information during debugging. For example, the build system optimizes out some variables, preventing you from inspecting them. Also, code re-ordering can make it more difficult to step through the code; stack traces may not be reliable.
android:debuggable in your application manifest's
tag will cause this variable to default to
debug instead of
release. Override this
default value by setting
This variable stores a set of C compiler flags that the build system passes to the compiler
when compiling any C or C++ source code for any of the modules. You can use this variable to change
the build of a given module according to the application that needs it, instead of having to modify
Android.mk file itself.
All paths in these flags should be relative to the top-level NDK directory. For example, if you have the following setup:
To specify in
foo/Android.mk that you want to add the path to the
during compilation, you should use:
APP_CFLAGS += -Isources/bar
APP_CFLAGS += -I$(LOCAL_PATH)/../bar
-I../bar will not work since it is equivalent to
Note: This variable only works on C, not C++, sources in
android-ndk-1.5_r1. In all versions after that one,
APP_CFLAGS matches the full Android
This variable contains a set of C++ compiler flags that the build system passes to the compiler when building only C++ sources.
Note: In android-ndk-1.5_r1, this variable works on both C and
C++ sources. In all subsequent versions of the NDK,
APP_CPPFLAGS now matches the full
Android build system. For flags that apply to both C and C++ sources, use
A set of linker flags that the build system passes when linking the application. This variable is only relevant when the build system is building shared libraries and executables. When the build system builds static libraries, it ignores these flags.
By default, the NDK build system looks under
jni/ for a file named
If you want to override this behavior, you can define
APP_BUILD_SCRIPT to point to an
alternate build script. The build system always interprets a non-absolute path as relative to the
NDK's top-level directory.
By default, the NDK build system generates machine code for all non-deprecated ABIs. You can use
APP_ABI setting to generate machine code for specific ABIs. Table 1 shows the
APP_ABI settings for different instruction sets.
|Hardware FPU instructions on ARMv7 based devices||
|All supported instruction sets||
all is available starting from NDKr7.
You can also specify multiple values by placing them on the same line, delimited by spaces. For example:
APP_ABI := armeabi-v7a arm64-v8a x86
Note: If you are using Gradle's
directive to integrate an
ndk-build project into a Gradle project, then the
APP_ABI setting in your
Application.mk file is ignored. You can
configure ABIs to build in your Gradle scripts using an
abiFilters block or (if you
are using "Multiple APKs") an
abi block inside a
For the list of all supported ABIs and details about their usage and limitations, refer to ABI Management.
This variable contains the minimum Android platform version you want to support.
For example, a value of
android-15 specifies that your library uses
APIs that are not available below Android 4.0.3 (API level 15) and can't
be used on devices running a lower platform version. For a complete list
of platform names and corresponding Android system images, see
Android NDK Native APIs.
Instead of changing this flag directly, you should set the
minSdkVersion property in the
productFlavors blocks of your
build.gradle file. This makes sure your library
is used only by apps installed on devices running an
adequate version of Android. The ndk-build toolchain
uses the following logic to choose the minimum platform
version for your library based the ABI you're building and
minSdkVersion you specify:
If there exists a platform version for the ABI equal to
minSdkVersion, ndk-build uses that version.
Otherwise, if there exists platform versions lower than
minSdkVersionfor the ABI, ndk-build uses the highest of those platform versions. This is a reasonable choice because a missing platform version typically means that there were no changes to the native platform APIs since the previous available version.
Otherwise, ndk-build uses the next available platform version higher
By default, the NDK build system provides C++ headers for the minimal C++ runtime library
system/lib/libstdc++.so) provided by the Android system. In addition, it comes with
alternative C++ implementations that you can use or link to in your own applications.
APP_STL to select one of them. For information about the supported runtimes, and the
features they offer, see NDK Runtimes and
The equivalent of
Application.mk for your whole project.
For more information, see the documentation for this variable on
Define this variable as
4.9 to select that version of the GCC
compiler. Define this variable as
clang to select the Clang compiler, which is the
default value for NDK r13 and later.
Starting from Android 4.1 (API level 16), Android's dynamic linker supports position-independent
executables (PIE). From Android 5.0 (API level 21), executables require PIE.
To use PIE to build your executables, set the
-fPIE flag. This flag makes it harder to
exploit memory corruption bugs by randomizing code location. By default,
automatically sets this value to
true if your project targets
android-16 or higher.
You may set it manually to either
This flag applies only to executables. It has no effect when building shared or static libraries.
Note: PIE executables cannot run on Android releases prior to 4.1.
This restriction only applies to executables. It has no effect when building shared or static libraries.
Sets the default value of
LOCAL_THIN_ARCHIVE in the
Android.mk file for all
static library modules in this project. For more information, see the documentation for