I am building a daemon on Android Platform. For which I have cross compiled the existing code, which is present in Linux to Android. Please consider my below 2 cases -
I cross compile the code using Cmake with Android NDK-15 and push manually to the board on which Android Code is available. The path in which we push is /system/lib. Then if I try to execute my daemon (which is also pushed manually to /system/bin ) everything works fine.
But,
2 The cross compiled library have been pushed into the AOSP code by writing an Android.mk file written in vendor specific folder. I have used BUILD_PREBUILTS method and was successfully able to push the libraries to /system/lib. Now, when I try to execute my application (Compiled with CMake ) I get a linker error.
Below is the error which I get ( Reference Example ) -
Below is the folder structure -
Total Number of folders - 3
a. abc folder which produces output libabc.so and links to libdef.so and
libghi.so
b. def folder which produces output libdef.so
c. ghi folder which produces output libghi.so
When I push all the 3 libraries (libabc.so, libdef.so, libghi.so ) directly in /system/lib and my executable (drive_test) which links all the 3 libraries, I have no issue. But, when I push it along with AOSP build I get the following error on execution of the executable (drive_test) -
a. Unable to link ../abc/def.so file.
I am unable to debug how to solve this linker issue. I am not getting whether it is because of CMake (or) any other issue.
If you're trying to make a system daemon (something that goes in /system/bin), don't use the NDK. Just use the AOSP build system.
In mydaemon/Android.bp (make sure to add this path to the root Android.bp file):
cc_library {
name: "libmylib",
srcs: ["mylib.cpp"],
}
cc_binary {
name: "mydaemon",
srcs: ["mydaemon.cpp"],
shared_libs: ["libmylib"],
}
The build system will deal with getting libraries and binaries into the right place for you.
Related
I am trying to build an executable for Android with cross compiling, everything works but the executable complains that it could not find the .so file it needs, which is in the same directory as the executable.
So what I did is to add the following lines
set(TARGET myapp)
# following 4 lines added to add RPATH of ./ to the binary
# so it searches the .so in the same directory
SET(CMAKE_SKIP_BUILD_RPATH FALSE)
SET(CMAKE_SKIP_RPATH FALSE)
set(CMAKE_INSTALL_RPATH $ORIGIN)
SET(CMAKE_BUILD_WITH_INSTALL_RPATH ON)
# add source code to target
add_executable(${TARGET} src.cpp)
...
However, it builds the executable, but RPATH seems not working no matter how I play with the four lines above, I just could not find any RPATH info in the binary using readelf or objdump.
I also tried set_target_properties(${TARGET} PROPERTIES INSTALL_RPATH $ORIGIN) but still not working.
Did I miss use anything here for RPATH configuration?
update
just to note that if I build the app for host(Linux) (using the same cmake file except using the android ndk tool chain) then everything is fine, I see $ORIGIN in the binary RPATH using readelf.
although i dont know what is been done in android ndk tool chain
This is probably not what you want:
(I am mentioning it just to be complete with my answer)
I assume that $ORIGIN is an environment variable. If that is the case you need to explain to CMake that it is such an variable. You can use $ENV{VAR} to do this, e.g.:
set(CMAKE_INSTALL_RPATH $ENV{ORIGIN})
This is probably what you want:
Ofcourse if the variable is not accessible during CMake generation step. You can try to use bracket arguments, however I do not think that alone would work (see last note at the bottom). Bracket arguments [=[...]=] tell CMake to skip the evaluation, because $ is a special character. e.g.:
set(CMAKE_INSTALL_RPATH [=[$ORIGIN]=])
To understand what [=[]=] do here is a simple example:
set(FOO "bar")
message(STATUS ${FOO})
message(STATUS [=[${FOO}]=])
Should output
bar
${FOO} #<-- evaluation of ${FOO} was skipped
Also if I'm not mistaken you also need to pass $ORIGIN to linker with single quotes so that it doesn't get evaluated during linking, i.e.
'$ORIGIN'
#and not $ORIGIN
I'm working on an Android project which uses a Java class that is a wrapper on a C++ library. The C++ library is a company internal library and we have access to its source code, but in the Android project it is only dynamically linked, so it is used only in the form of headers (.h) and shared objects (.so). Having access to the library source code, is it possible to specify to Android Studio the path to the source code so I can step inside the library using the debugger?
The debugger works, I can step inside the Java_clory_engine_sdk_CloryNative_nativeInit function, but I would also like to further debug the library corresponding to the Clory::Engine class which, as I mentioned, is an internal library we have source code access to.
For example, Clory::Engine::instance is part of the library and I would like to specify to Android Studio the location of the CloryEngine.cpp file so I can step inside Clory::Engine::instance with the debugger, thus debugging this static member function.
I am using Android Studio 3.1.4.
Is this possible?
EDIT:
The clory-sdk.gradle file specifies the CMakeLists.txt file which configures the C++ layer.
externalNativeBuild {
cmake {
path "CMakeLists.txt"
}
}
So I am using an internal application which uses the Clory SDK. Inside the app.gradle file I use:
dependencies {
...
compile project(':clory-sdk-core')
compile project(':clory-sdk')
...
}
so I don't think we're using the aars for the app.gradle project. The aars are shipped to the client, but we are using app.gradle project to test our little SDK functionalities before doing that. The JNI layer is inside clory-sdk-core project.
EDIT 2:
Here is the CMakeLists.txt which handles the JNI layer:
cmake_minimum_required(VERSION 3.4.1)
set(CMAKE_AUTOMOC ON)
set(CMAKE_INCLUDE_CURRENT_DIR ON)
set(CMAKE_BUILD_TYPE Debug)
add_library(
clory-lib
SHARED
# JNI layer and other helper classes for transferring data from Java to Qt/C++
src/main/cpp/clory-lib.cpp
src/main/cpp/JObjectHandler.cpp
src/main/cpp/JObjectResolver.cpp
src/main/cpp/JObjectCreator.cpp
src/main/cpp/DataConverter.cpp
src/main/cpp/JObjectHelper.cpp
src/main/cpp/JEnvironmentManager.cpp
)
find_library(
log-lib
log
)
target_compile_options(clory-lib
PUBLIC
-std=c++11
)
# Hardcoded for now...will fix later...
set(_QT_ROOT_PATH /Users/jacob/Qt/5.8)
if(${ANDROID_ABI} MATCHES ^armeabi-v7.*$)
set(_QT_ARCH android_armv7)
elseif(${ANDROID_ABI} MATCHES ^x86$)
set(_QT_ARCH android_x86)
else()
message(FATAL_ERROR "Unsupported Android architecture!!!")
endif()
set(CMAKE_FIND_ROOT_PATH ${_QT_ROOT_PATH}/${_QT_ARCH})
find_package(Qt5 REQUIRED COMPONENTS
Core
CONFIG
)
target_include_directories(clory-lib
PUBLIC
${CMAKE_CURRENT_LIST_DIR}/src/main/cpp
)
set(_CLORYSDK_LIB_PATH ${CMAKE_CURRENT_LIST_DIR}/src/main/jniLibs/${ANDROID_ABI})
target_link_libraries(clory-lib
${log-lib}
-L${_CLORYSDK_LIB_PATH}
clorysdk
Qt5::Core
)
The library clorysdk is actually our internal library I was talking about, which contains e.g. Clory::Engine::instance I would like to step into with the debugger. It was built with qmake and is built in debug mode (CONFIG+=debug was added in the effective qmake call).
EDIT 3:
In the LLDB session which has opened after it hit the Java_clory_engine_sdk_CloryNative_nativeInit breakpoint, I got the following:
(lldb) image lookup -vrn Clory::Engine::instance
2 matches found in /Users/jacob/.lldb/module_cache/remote-android/.cache/6EDE4F0A-0000-0000-0000-000000000000/libclorysdk.so:
Address: libclorysdk.so[0x0001bb32] (libclorysdk.so..text + 8250)
Summary: libclorysdk.so`Clory::Engine::instance(Clory::Engine::Purpose)
Module: file = "/Users/jacob/.lldb/module_cache/remote-android/.cache/6EDE4F0A-0000-0000-0000-000000000000/libclorysdk.so", arch = "arm"
Symbol: id = {0x0000005e}, range = [0xcb41eb32-0xcb41ebc0), name="Clory::Engine::instance(Clory::Engine::Purpose)", mangled="_ZN4Clory2Engine8instanceENS0_7PurposeE"
Address: libclorysdk.so[0x0001b82c] (libclorysdk.so..text + 7476)
Summary: libclorysdk.so`Clory::Engine::instance(Clory::RuntimeConfiguration const&, Clory::Engine::Purpose)
Module: file = "/Users/jacob/.lldb/module_cache/remote-android/.cache/6EDE4F0A-0000-0000-0000-000000000000/libclorysdk.so", arch = "arm"
Symbol: id = {0x000000bd}, range = [0xcb41e82c-0xcb41e970), name="Clory::Engine::instance(Clory::RuntimeConfiguration const&, Clory::Engine::Purpose)", mangled="_ZN4Clory2Engine8instanceERKNS_20RuntimeConfigurationENS0_7PurposeE"
(lldb) settings show target.source-map
target.source-map (path-map) =
First of all, there was no CompileUnit section in the result of the command image lookup -vrn Clory::Engine::instance. How is this possible to have no source-map defined(second lldb command) if the libclorysdk.so was built in Debug mode? Is it possible to explicitly set it so that the debugger would search there for the library's source files?
EDIT 4:
After searching more I found out that the process of creating the APK actually strips the *.so libraries from their debugging symbols. libclorysdk.so built in debug mode has about 10MB while the libclorysdk.so file which I extracted after unarchiving the generated *.apk file is just 350KB.
As stated here, running greadelf --debug-dump=decodedline libclorysdk.so on the debug version outputs references to the source files, but if the command is run on the *.apk extracted library, it outputs nothing.
Is there a way to stop Android Studio from stripping the *.sos? I tried How to avoid stripping for native code symbols for android app but didn't have any effect, *.apk file is the same size as before and debugging the native libraries still doesn't work.
I'm using Gradle 3.1.4.
EDIT 5:
The stripping solution works, but in my case, it needed a Clean & Build before hitting the breakpoints in the library. Deploying *.sos which are not stripped is allowing you to have debugging sessions and step inside the native libraries.
Note:
If the libraries are built using the Qt for Android toolchain, the *.sos deployed to $SHADOW_BUILD/android-build are also stripped(where $SHADOW_BUILD is the build directory usually starting with build-*). So in order to debug those you should copy them from outside the android-build directory where each *.so is generated.
The debug info records the location of the source files when they were built.
(lldb) image lookup -vrn Clory::Engine::instance
The CompileUnit line shows the source file. Suppose it says:
"/BuildDirectory/Sources/Clory/CloryEngine.cpp"
Let's assume you have the source on your machine here:
"Users/me/Sources/Clory"
So you can tell lldb: find the source file rooted at /BuildDirectory/Sources/Clory in Users/me/Sources/Clory instead.
(lldb) settings set target.source-map /BuildDirectory/Sources/Clory Users/me/Sources/Clory
You can use these commands in the lldb console of Android Studio or put into a .lldbinit file for general use.
If there no debug symbols available, you might have to build the referenced library in debug mode.
Either with -DCMAKE_BUILD_TYPE=DEBUG:
defaultConfig {
externalNativeBuild {
cmake {
arguments "-DANDROID_TOOLCHAIN=gcc", "-DCMAKE_BUILD_TYPE=DEBUG"
cppFlags "-std=c++14 -fexceptions -frtti"
}
}
}
externalNativeBuild {
cmake {
path file('src/main/cpp/CMakeLists.txt')
}
}
Or add this to the CMakeLists.txt of the library:
set(CMAKE_BUILD_TYPE Debug)
See the CMake documentation and Symbolicating with LLDB.
Elsewhere it explains (lldb) settings set target.source-map /buildbot/path /my/path:
Remap source file path-names for the debug session. If your source files are no longer located in the same location as when the program was built --- maybe the program was built on a different computer --- you need to tell the debugger how to find the sources at their local file path instead of the build system's file path.
There's also (lldb) settings show target.source-map, to see what is mapped.
(lldb) set append target.source-map /buildbot/path /my/path seems rather suitable, in order not to overwrite existing mappings.
My project is fairly simple. I have an app that includes a library written based on integration platfrom so it looks something like this:
My app
----> Extension
----> Main library
The app is cross-compiled to Android. All of them are based on CMake. I'm using CLion as an IDE. I've added a profile with custom toolchain required to build for Android (that is clang, clang++ for apropiate platform, cmake from Android SDK and make from Android NDK r20b). Problem is I have to call CMake 3 times (reload it in CLion) before it generates all of the files needed. Whole file is listed below.
On the first run it ignores the fact it is build for android (doesn't go into if (ANDROID) ) and copies the prebuilt sub-executable for linux (default)
On the second run it ignores the needed android.toolchain.cmake and when build on this stage it fails to add android headers to search path BUT chooses correct prebuilt sub-executable
On the the third run it uses the android.toolchain.cmake file AND chooses correct sub-executable.
After that I can hit build and everything compiles correctly.
The CMake I have:
add_executable(androidApp main.cpp)
target_include_directories(androidApp
PUBLIC
../submodules/exten/src/libraries/main_lib/lib/include
../submodules/exten/src/libraries/main_lib/sdk/rlogging/include) //Headers from main library
target_link_libraries(androidApp
PRIVATE
exten) //Extension
install(TARGETS androidApp DESTINATION ${CMAKE_SOURCE_DIR}/bin)
install(FILES ../submodules/exten/src/libraries/main_lib/integration_app/resources/someFile.zip DESTINATION ${CMAKE_SOURCE_DIR}/bin)
install(FILES ../resources/someFile2.zip DESTINATION ${CMAKE_SOURCE_DIR}/bin/resources)
file(MAKE_DIRECTORY ${CMAKE_SOURCE_DIR}/bin/bootsafe)
file(WRITE ${CMAKE_SOURCE_DIR}/bin/bootsafe/dummy "") //Required dir
add_custom_command(TARGET dongleApp POST_BUILD
COMMAND ${CMAKE_SOURCE_DIR}/ndk/android-ndk-r20b/toolchains/llvm/prebuilt/linux-x86_64/arm-linux-androideabi/bin/strip --strip-debug dongleApp
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
COMMENT "Stripping debug symbols")
if (ANDROID)
target_link_libraries(androidApp
PRIVATE
log)
endif (ANDROID) //Linking android lib
On different CMake (on the main library level) here's how the choosing on correct prebuilt is written
if(NOT ANDROID)
set(PREBUILD_NAME "linux")
else()
if(ANDROID_ABI STREQUAL "x86_64")
set(PREBUILD_NAME "android-x86")
else()
set(PREBUILD_NAME "android-arm")
endif()
endif()
The command that is used to generate makefiles:
/home/gravlok/companyName/app_v2/sdk/cmake/3.10.2.4988404/bin/cmake
-DCMAKE_BUILD_TYPE=Debug
-DCMAKE_MAKE_PROGRAM=/home/gravlok/companyName/app_v2/ndk/android-ndk-r20b/prebuilt/linux-x86_64/bin/make
-DCMAKE_C_COMPILER=/home/gravlok/companyName/app_v2/ndk/android-ndk-r20b/toolchains/llvm/prebuilt/linux-x86_64/bin/armv7a-linux-androideabi28-clang
-DCMAKE_CXX_COMPILER=/home/gravlok/companyName/app_v2/ndk/android-ndk-r20b/toolchains/llvm/prebuilt/linux-x86_64/bin/armv7a-linux-androideabi28-clang++
-DANDROID=ON
-DCMAKE_TOOLCHAIN_FILE=/home/gravlok/companyName/app_v2/ndk/android-ndk-r20b/build/cmake/android.toolchain.cmake -DANDROID_PLATFORM=android-28
-G "CodeBlocks - Unix Makefiles"
/home/gravlok/companyName/app_v2
Why do I need to run it 3 times in order to configure correctly?
I am facing the following issue when trying to compile a c program using openssl for android x-86. I set up the environment variables as follows using the following script:
setenv-android.sh
After running the script I have the following environment.
./setenv-android_x86.sh
find: /dev/fd/3: Not a directory
find: /dev/fd/4: Not a directory
Error: FIPS_SIG does not specify incore module. Please edit this script.
ANDROID_NDK_ROOT: /opt/android-ndk-r9d-x86
ANDROID_ARCH: arch-x86
ANDROID_EABI: x86-4.6
ANDROID_API: android-18
ANDROID_SYSROOT: /opt/android-ndk-r9d-x86/platforms/android-18/arch-x86
ANDROID_TOOLCHAIN: /opt/android-ndk-r9d-x86/toolchains/x86-4.6/prebuilt/darwin-x86_64/bin
FIPS_SIG:
CROSS_COMPILE: i686-linux-android-
ANDROID_DEV: /opt/android-ndk-r9d-x86/platforms/android-18/arch-x86/usr
However when trying to compile with the following command I get the following error:
pwd
/opt/android-ndk-r9d-x86/bin
./i686-linux-android-gcc Test.c -o test -lcrypto
fatal error: openssl/conf.h: No such file or directory
When I locate for the openssl/conf.h I see the file is available in many places:
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.8.sdk/usr/include/openssl/conf.h
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk/usr/include/openssl/conf.h
/data/local/arm/ssl/include/openssl/conf.h
/data/local/ssl/include/openssl/conf.h
/openssl/include/openssl/conf.h
/openssl-1.0.1e/include/openssl/conf.h
/openssl-1.0.1g/include/openssl/conf.h
/opt/local/include/openssl/conf.h
/usr/include/openssl/conf.h
/usr/local/include/openssl/conf.h
/usr/local/ssl/android-14/include/openssl/conf.h
/usr/local/ssl/android-18/include/openssl/conf.h
/usr/local/ssl/android-18-x86/include/openssl/conf.h
/usr/local/ssl/include/openssl/conf.h
I think the proper path is this:
/usr/local/ssl/android-18-x86/include/openssl/conf.h
I tried with the -L option but with no luck.
-L/usr/local/ssl/android-18-x86/include/
Can anybody please explain how to setup the path properly to solve this issue. (finally there is no issue with the C code as it compiles properly with gcc)
You are compiling your code using the Android NDK, which creates a "virtual" compiling environment by placing everything you need to compile for android into the ${ANDROID_SYSROOT} directory.
Those directories you listed are outside that sysroot, and therefore are not available to the build system, hence the errors. You must install OpenSSL for Android and putting the resulting headers and binaries there. You might follow this guide to assist you in that.
I tried building i686-linux-android-gfortran using build-gcc.sh following this
(it's for androdindk-7b) but I get error about link.h. I added link.h from here, but it gives further more errors.
Has anyone tried enabling i686-linux-android-gfortran for x86 Android?
From https://groups.google.com/forum/#!msg/android-ndk/QR1qiN0jIpE/g0MHkhTd4YMJ as selalerer suggested. I didn't try this, so I'm posting as a community wiki for reference purposes.
Fortran for x86 Android
=================
The guide is based on this one, many thanks to Phil:
Compiling Android NDK with Objective-C-enabled gcc errors
1) Download and unpack Android NDK 'android-ndk-r8c', (the older -r8b NDK won't work due to missing link.h!):
wget http://dl.google.com/android/ndk/android-ndk-r8c-linux-x86.tar.bz2
2) Create somewhere a folder called 'toolchain-src' (e.g. inside the folder android-ndk-r8c),
'cd' to this new folder
3) Make sure to have git installed ('yum install git' or whatever..) and download
the toolchain sources:
git clone https://android.googlesource.com/toolchain/build.git
git clone https://android.googlesource.com/toolchain/gmp.git
git clone https://android.googlesource.com/toolchain/gdb.git
git clone https://android.googlesource.com/toolchain/mpc.git
git clone https://android.googlesource.com/toolchain/mpfr.git
git clone https://android.googlesource.com/toolchain/expat.git
4) Create the folder 'binutils', 'cd' to this directory, unpack
binutils-2.23 there:
wget ftp.gnu.org/gnu/binutils/binutils-2.23.tar.gz
tar -xvzf binutils-2.23.tar.gz
You should now have a folder toolchain-src/binutils/binutils-2.23
5) Change to folder toolchain-src/build, edit the Makefile.in, changing the line:
--with-gnu-as --with-gnu-ld --enable-languages=c,c++
to
--with-gnu-as --with-gnu-ld --enable-languages=c,c++,fortran
6) In the file android-ndk-r8c/build/tools/build-mingw64-toolchain.sh change the line:
var_append GCC_CONFIGURE_OPTIONS "--enable-languages=c,c++"
to
var_append GCC_CONFIGURE_OPTIONS "--enable-languages=c,c++,fortran"
7) In the file android-ndk-r8c/build/tools/build-gcc.sh, change the line:
EXTRA_CONFIG_FLAGS=$EXTRA_CONFIG_FLAGS" --disable-libquadmath --disable-plugin"
to
EXTRA_CONFIG_FLAGS=$EXTRA_CONFIG_FLAGS" --disable-libquadmath --disable-libquadmath-support --disable-plugin"
8) In the file android-ndk-r8c/build/tools/build-host-gcc.sh, change the line:
ARGS=$ARGS" --enable-languages=c,c++"
to
ARGS=$ARGS" --enable-languages=c,c++,fortran"
And change the line
ARGS=$ARGS" --disable-libquadmath --disable-plugin --disable-libitm --disable-bootstrap"
to
ARGS=$ARGS" --disable-libquadmath --disable-libquadmath-support --disable-plugin --disable-libitm --disable-bootstrap"
9) Build your new toolchain:
/your/path/to/android-ndk-r8c/build/tools/build-gcc.sh -j1 --gmp-version=5.0.5 --mpfr-version=2.4.2 --mpc-version=0.8.1 --binutils-version=2.23 --gdb-version=7.3.x /your/path/to/toolchain-src /your/path/to/android-ndk-r8c x86-4.7
(don't worry about messages like 'expr: warning: unportable BRE:')
10) And go down to your knees in front of the screen, praying to the Lord that somehow these
countless configure scripts doing checks that nobody needs, using an ugly shell language
that cooks your brain with indentation going from right to left, will somehow manage to
compile a zillion of far too small files (so that 10% of the time is spent on compilation
and 90% on starting up GCC), and after an hour of watching progress with
tail -F /tmp/ndk-YourUserName/build/toolchain/config.log
your toolchain will be magically ready. You'll find it in the android-ndk-r8c/toolchains folder.
11) Finally, 'cd' to the folder
'/your/path/to/android-ndk-r8c/toolchains/x86-4.7/prebuilt/linux-x86/i686-linux-android'
and run this command:
ln -s ../libexec libexec
Without this command, it may happen that g++ raises the error message
"g++: fatal error: -fuse-linker-plugin, but liblto_plugin.so not found".
Using strace, I found that g++ looks in the wrong folder, but the link
above lets it find the file liblto_plugin.so nevertheless.
And here are a few lessons learned on the way, so that Google finds this page:
*) To speed up the compilation, you can remove the '-j1'. But only after you got
it to work once, since building in parallel on multiple CPU cores was reported to
cause additional troubles.
*) The error message "Link tests are not allowed after GCC_NO_EXECUTABLES" shows up
when linking fails for x86 (works for ARM). The reason is that GCC does not include
the proper ANDROID_STARTFILE_SPEC and ANDROID_ENDFILE_SPEC from
gcc-4.6.1/gcc/config/linux-android.h. GCC 4.6.1 only specifies them for ARM, but not
for i386, GCC 4.8.0 however does. The GCCs downloaded from Google also do,
so best use Google's GCC.
*) The error message "fatal error: link.h: No such file or directory" also happens
with Google's GCC, and apparently (http://gcc.gnu.org/bugzilla/show_bug.cgi?id=50877)
only when you enable additional languages like objc or fortran.
The bug thread is here: http://gcc.gnu.org/ml/gcc-bugs/2012-08/msg00494.html
MIPS has link.h in android-ndk-r8b/platforms/android-9/arch-mips/usr/include
In android-ndk-r8c, link.h is now also present in android-9/arch-x86/usr/include/link.h,
so this bug was fixed.
*) The error message "fatal error: quadmath_weak.h: No such file or directory":
It also happens with the latest gcc-4.8, so we can just continue using Googles GCC 4.7.
Google itself uses --disable-libquadmath, but we additionally need --disable-libquadmathsupport
(see http://gcc.gnu.org/bugzilla/show_bug.cgi?id=47648). So this needs to be added in
android-ndk-r8c/build/tools/build-gcc.sh
and
android-ndk-r8c/build/tools/build-host-gcc.sh
*) The error message "error: Pthreads are required to build libatomic"
Happens when building the ARM version of gcc-4.8 downloaded from gnu.org,
better stay with Google's GCCs.
*) The GCC that came with android-ndk-r8c didn't work for me (error message about
libstdc++.so.6 being too old), while the one in android-ndk-r8b worked
without problems. Since the android-ndk should support as many environments
as possible, I'm not sure why the Googlers decided to depend on a newer libstdc++,
but the good news are that building your own toolchain solves the issue.
*) If you get an error while compiling generic-morestack.c, then replace
#ifdef linux
// On Linux, the first two real time signals are used by the NPTL
with
#if defined(GLIBC) && defined(linux)
// On Linux, the first two real time signals are used by the NPTL