Android
NDK

Android NDK + CMake で C/C++ 11 コンソールプログラムを Android 実機で実行する

漢なら, Android でも Gradle や実機上の Java モジュールに依存せずにコンソール C/C++ アプリを実機でユニットテストし, Linux での CMake で C/C++ 開発と同じような開発スキーム確立したいですね!

やりましょう!

背景

普段 IDE は使わず, macOS or Linux でターミナル(vim, cmake)で C/C++ 開発をしているので, Android 向けも同様な環境で開発できるようにしたい.

Gradle を使わず, Makefile or Ninja だけでビルドできるようにしたい

Java レイヤーをエントリポイントとしても良いが, Java 部分を書くのがめんどい.

Android は ARMv8(64bit)が主流であるし, NEON 命令を使ったりもするかもなので, エミュレータではなく実機で動かす必要性が高い.
(ARM 環境だけであれば, ラズパイのように ARMv8 Linux box を使うというてもあるかも. また, 最新 ARM64bit エミュレータは NEON 命令も扱えるようになったかも?)

要件

CMake bootstrap

CMakeLists.txt は, だいたい今までの C/C++ アプリと同じように記述できます.
(Android に特化した設定が必要な場合は別途記述)

Android SDK に cmake(+ ninja)が含まれているので, それを使って Android 用の設定を cmake configure のオプションに指定します.

https://developer.android.com/ndk/guides/cmake.html

にオプションのリストがあります.
最低限, 以下のような感じにすればビルド用 Makefile が生成されます.

# bootstrap-android.sh

## Please edit android sdk/ndk/cmake path
ANDROID_SDK_ROOT=$HOME/Android/Sdk/
ANDROID_NDK_ROOT=$HOME/Android/Sdk/ndk-bundle
CMAKE_BIN=$ANDROID_SDK_ROOT/cmake/3.6.4111459/bin/cmake

rm -rf build-android

$CMAKE_BIN \
-DCMAKE_TOOLCHAIN_FILE=$ANDROID_NDK_ROOT/build/cmake/android.toolchain.cmake \
-DANDROID_ABI=arm64-v8a \
-DANDROID_NATIVE_API_LEVEL=24 \
-DANDROID_STL=c++_static \
-Bbuild -H.

STL の選択

c++_shared だと, Android 実機側の C++ STL ランタイム .so と互換性が無く実行時エラーが出ます.

c++_static でコンパイルするようにします. 静的 STL リンクだとコンパイルエラーが出るような C/C++ アプリは今回は Android で動かすのはあきらめましょう...

gnustl も, ものによってはコンパイルエラーになります(e.g. json.hpp など https://github.com/nlohmann/json ). サードパーティライブラリを使うときは,
Android でもコンパイルでき, 各種 STL 環境でも動くものを選びましょう.

実行する

Android 実機を USB でつなぎ,

adb push/sdcard あたりにバイナリを開発 PC から Android 実機に転送します.

adb shell で Android 実機になり,

su で root にになり, バイナリを /data/local/tmp に移動して chmod +x a.out と実行権限を付けて, 動かします.

$ su
# cd /data/loca/tmp
# ./a.out

これで Android 実機で C/C++ プログラムが動きます!

TODO

  • OpenGL みたいな画面を出すようなアプリは別途考える. https://qiita.com/syoyo/items/85f01123c7d43298a85d
    • Vulkan offscreen ならいけるかも?
  • Jenkins あたりで CI ビルドするようにしたい.
  • HiKey 960 のアップデートを極めてくれる, 優秀な Android 開発ボード若人を探す旅に出たい.
  • ANDROID_STLsystem にし, NanoSTL https://github.com/lighttransport/nanostl を使うようにして STL 非依存な Android C++ アプリに挑戦したい.