-----------------
英文文档见android-ndk-r5b的documentation.html
属于Android Native Development Kit (NDK)的一部分
见http://developer.android.com/sdk/ndk/(需要代理)
翻译仅个人见解
-----------------
USING THE ANDROID TOOLCHAIN AS A STANDALONE COMPILER
使用Android工具链作为独立编译器
======================================================
WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
警告:
SUPPORT FOR THIS FEATURE IS STILL IN BETA AND ONLY APPLIES TO arm-linux-androideabi-4.4.3
这项特性的支持尚在测试中,只适用于arm-linux-androideabi-4.4.3
IF YOU ENCOUNTER A PROBLEM WITH THE METHODS DESCRIBED HERE, PLEASE CONTACT THE SUPPORT FORUM AT
如果你遇到这里描述到的问题,请联系支持论坛,在
android-ndk@googlegroups.com
WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
It is now possible to use the toolchain provided with the Android NDK as a standalone compiler. This can be useful if you already have your own build system, and only need to ability to invoke the cross-compiler to add support to Android for it.
现在可以使用Android NDK提供的工具链作为独立编译器。这可能有用,如果你已经拥有你自己的构建系统(注:这里可能指使用不同于NDK的构建系统),只需要使它能调用交叉编译器(注:即所生成的目标二进制文件架构和开发平台不同的编译器),以使其添加对Android的支持。
A typical use case if invoking the 'configure' script of an open-source library that expects a cross-compiler in the CC environment variable.
一个典型用例,如果要调用一个开源库的configure脚本,则期待在CC环境变量中提供交叉编译器(注:很多开源库都喜欢使用configure脚本即时生成Makefile)。
This document explains how to do that:
这个文档解释它如何工作:
1/ Selecting your sysroot:
1、选择你的sysroot:
--------------------------
The first thing you need to know is which Android native API level you want to target. Each one of them provides a different various APIs, which are documented under doc/STABLE-APIS.html, and correspond to the sub-directories of $NDK/platforms.
首先你需要知道的事情是你的目标平台是哪个Android原生API级别。它们当中提供不同种类的API,在doc/STABLE-APIS.html下有文档,对应于$NDK/platforms下的子目录。
This allows you to define the path to your 'sysroot', a GCC term for a directory containing the system headers and libraries of your target. Usually, this will be something like:
允许你定义你的sysroot目录,一个GCC术语(注:应该是指针对那些非标准,依赖硬件,而且可能会被修改的系统头文件)表示包含你的目标平台的系统头文件和库的目录。通常,它像这样子:
SYSROOT=$NDK/platforms/android-<level>/arch-<arch>/
Where <level> is the API level number, and <arch> is the architecture ("arm" being currently supported). For example, if you're targetting Android 2.1 (a.k.a. Froyo), you would use:
这里<level>是API级别号,而<arch>是架构(当前支持的是“arm”)。例如,如果你的目标平台是Android 2.1(代号Froyo),你将使用:
SYSROOT=$NDK/platforms/android-8/arch-arm
2/ Invoking the compiler (the hard way):
2、调用编译器(复杂方式):
----------------------------------------
Invoke the compiler using the --sysroot option to indicate where the system files for the platform you're targetting are located. For example, do:
使用--sysroot选项调用编译器以指出你的目标平台的系统文件放在哪里。例如,这样执行:
export CC="$NDK/toolchains/<name>/prebuilt/<system>/bin/<prefix>gcc --sysroot=$SYSROOT"
$CC -o foo.o -c foo.c
Where <name> is the toolchain's name, <system> is the host tag for your system, and <prefix> is a toolchain-specific prefix. For example, if you are on Linux using the NDK r5 toolchain, you would use:
这里<name>是工具链的名称,<system>是你的系统的主机标签,而<prefix>是工具链的特定前缀。例如,如果你在Linux上使用NDK r5工具链,你将使用:
export CC="$NDK/toolchains/arm-linux-androideabi-4.4.3/prebuilt/linux-x86/bin/arm-linux-androideabi-gcc --sysroot=$SYSROOT"
As you can see, this is rather verbose, but it works!
正如你可以看到的,这非常啰嗦,但它可以工作!
3/ Invoking the compiler (the easy way):
3、调用编译器(简单方式):
----------------------------------------
The NDK allows you to create a "customized" toolchain installation to make life easier. For example, consider the following command:
NDK允许你创建一个“定制”的工具链安装版进行简化。例如,考虑以下命令:
$NDK/build/tools/make-standalone-toolchain.sh --platform=android-5 --install-dir=/tmp/my-android-toolchain
This will create a directory named /tmp/my-android-toolchain containing a copy of the android-5/arch-arm sysroot, and of the toolchain binaries.
这将创建一个名为/tmp/my-android-toolchain的目录,包含android-5/arch-arm的sysroot和工具链二进制文件的副本。
You can later use it directly with something like:
以后你可以用类似这样的方法直接使用它:
export PATH=/tmp/my-android-toolchain/bin:$PATH
export CC=arm-linux-androideabi-gcc
Note that without the --install-dir option, make-standalone-toolchain.sh will create a tarball in /tmp/ndk/<toolchain-name>.tar.bz2. This allows you to archive and redistribute the binaries easily.
注意如果不用--install-dir选项,make-standalone-toolchain.sh将创建一个/tmp/ndk/<toolchain-name>.tar.bz2的压缩包。允许你简单地归档和重新分发二进制文件。
Use --help for more options and details.
更多选项和详细信息请使用--help。
IMPORTANT: The toolchain binaries do not depend or contain host-specific paths, in other words, they can be installed in any location, or even moved if you need to.
重要:工具链的二进制文件不依赖或包含主机特定的路径,也就是说,它们可以安装在任意路径,如果你需要的话甚至可以被移动。(注:应该指它通过相对路径进行文件搜索,或者说它是绿色版)
NOTE: You can still use the --sysroot option with the new toolchain, but it is now simply optional!
注意:你仍然可以对新的工具链使用--sysroot选项,但现在简单地成为可选了!
4/ ABI Compatibility:
4、ABI(注:应用程序二进制接口)兼容性:
---------------------
The machine code generated by the toolchain should be compatible with the official Android 'armeabi' ABI (see docs/CPU-ARCH-ABIS.html) by default.
工具链生成机器代码默认应该兼容官方的Android “armeabi” ABI(见docs/CPU-ARCH-ABIS.html)
It is recommended to use the -mthumb compiler flag to force the generation of 16-bit Thumb-1 instructions (the default being 32-bit ARM ones).
建议使用-mthumb编译器开关强制生成16位Thumb-1指令(默认是32位ARM指令)
If you want to target the 'armeabi-v7a' ABI, you will need ensure that the following two flags are being used:
如果你打算的目标平台是armeabi-v7a ABI,你将需要确保使用了以下两个开关:
CFLAGS='-march=armv7-a -mfloat-abi=softfp'
Note: The first flag enables Thumb-2 instructions, and the second one enables H/W FPU instructions while ensuring that floating-point parameters are passed in core registers, which is critical for ABI compatibility. Do *not* use these flags separately!
注意:第一个开关打开Thumb-2指令功能,而第二个开关打开H/W浮点处理器指令功能,确保用核心寄存器传递浮点参数,它对于ABI兼容性来说是关键。不要分开使用这些开关!
If you want to use Neon instructions, you will need one more compiler flag:
如果你想使用Neon指令(注:ARM的单指令多数据技术),你需要再增多一个编译器开关:
CFLAGS='-march=armv7-a -mfloat-abi=softfp -mfpu=neon'
Note that this forces the use of VFPv3-D32, as per the ARM specification.
注意它强制使用VFPv3-D32(注:VFPv3是vector floating point v3的缩写,即向量浮点第三版,D32应该是指32个双精度浮点寄存器),根据ARM规范。
Also, is is *required* to use the following linker flags that routes around a CPU bug in some Cortex-A8 implementations:
还有,需要使用以下链接器开关,绕过某些Cortex-A8实现的CPU缺陷。
LDFLAGS='-Wl,--fix-cortex-a8'
If none of the above makes sense to you, it's probably better not to use the standalone toolchain, and stick to the NDK build system instead, which will handle all the details for you.
如果上面的东西对你不起作用,最好不要使用独立工具链,还是坚持使用NDK构建系统,它将为你处理所有细节。
5/ Warnings and Limitations:
5、警告和限制:
--------------------------
5.1/ Windows support:
5.1、Windows支持:
- - - - - - - - - - -
The Windows binaries do *not* depend on Cygwin. The good news is that they are thus faster, the bad news is that they do not understand the Cygwin path specification like /cygdrive/c/foo/bar (instead of C:/foo/bar).
Windows二进制文件不依赖于Cygwin。好消息是它们会跑得更快,而坏消息是它们不理解Cygwin的目录格式,像/cygdrive/c/foo/bar(但可以理解C:/foo/bar)
The NDK build system ensures that all paths passed to the compiler from Cygwin are automatically translated, and deals with other horrors for you. If you have a custom build system, you may need to deal with the problem yourself.
NDK构建系统确保从Cygwin中传递的所有路径被自动翻译,为你处理其它威胁。如果你拥有一个定制构建系统,你可能需要自己处理问题。
NOTE: There is no plan to support Cygwin / MSys at the moment, but contributions are welcome. Contact the android-ndk forum for details.
注意:现在没计划支持Cygwin / MSys,但欢迎贡献。详细请联系android-ndk论坛
5.2/ wchar_t support:
5.2、wchar_t支持:
- - - - - - - - - - -
As documented, the Android platform did not really support wchar_t until Android 2.3. What this means in practical terms is that:
正如文档所写的,Android平台在Android 2.3之前没有真正支持wchar_t。用实际的术语说,这意味着:
- If you target platform android-9 or higher, the size of wchar_t is 4 bytes, and most wide-char functions are available in the C library (with the exception of multi-byte encoding/decoding functions and wsprintf/wsscanf).
- 如果你的目标平台是android-9或更高,wchar_t的大小是4字节,则在C库中大多数宽字符函数可用(例外的是多字节的编码解码函数和wsprintf/wsscanf)
- If you target any prior API level, the size of wchar_t will be 1 byte and none of the wide-char functions will work anyway.
- 如果你的目标是较早的API级别,wchar_t的大小将是1字节,任何宽字符函数都不可工作。
We recommend any developer to get rid of any dependencies on the wchar_t type and switch to better representations. The support provided in Android is only there to help you migrate existing code.
我们建议所有开发者避免对wchar_t类型的依赖,而是转向更好的表示。在Android中提供的支持只出现在帮助你迁移现存代码的地方。
5.3/ Exceptions, RTTI and STL:
5.3、异常、RTTI和STL(注:标准模板库):
- - - - - - - - - - - - - - -
The toolchain binaries *do* support C++ exceptions and RTTI by default. They are enabled by default, so use -fno-exceptions and -fno-rtti if you want to disable them when building sources with them (e.g. to generate smaller machine code).
工具链二进制文件默认支持C++异常和RTTI(注:运行时类型信息)。它们默认是打开的,所以如果你想在构建使用它们的代码时关闭它们,请使用-fno-exceptions和-fno-rtti(例如,为了生成更小的机器代码)。
NOTE: You will need to explicitely link with libsupc++ if you use these features. To do this, use -lsupc++ when linking binaries, as in:
注意:你将需要显式地用libsupc++链接,如果你使用这些特性。为了做到这点,当链接二进制文件时使用-lsupc++,像这样:(注:这里要小心,是libsupc++不是libstdc++!)
arm-linux-androideabi-g++ .... -lsupc++
The toolchain also comes with a working GNU libstdc++ implementation, which provides a working C++ Standard Template Library implementation. You will need to explicitely link against -lstdc++ to use it.
工具链还带有一个可用的GNU libstdc++实现,它提供一个工作的C++标准模板库实现。你将需要显式地用-lstdc++链接以使用它。(注:貌似NDK文档说旧版Android不支持STL,或许NDK开发者意识到面向对象的C++不是太吸引人,毕竟和面向对象相比,C++开发者们更热衷于泛型)
Proper toolchain configuration to avoid these explicit link flags is planned for the future.
未来计划适当地配置工具链,以避免这些显式的链接开关。