Difference between revisions of "Build LDC for Android"

From D Wiki
Jump to: navigation, search
(Update to ldc 1.3)
(Update to final 1.3 release and llvm 4.0.1)
Line 1: Line 1:
 
This page will show you how to build an ldc cross-compiler for Android/ARM on linux or Windows 10 (by using the new bash on Ubuntu linux subsystem), along with how to build and run both the druntime/phobos tests and an Android D app using the cross-compiler.  [https://github.com/joakim-noah/android/releases Prebuilt native and cross-compilers are available here].
 
This page will show you how to build an ldc cross-compiler for Android/ARM on linux or Windows 10 (by using the new bash on Ubuntu linux subsystem), along with how to build and run both the druntime/phobos tests and an Android D app using the cross-compiler.  [https://github.com/joakim-noah/android/releases Prebuilt native and cross-compilers are available here].
  
All but one of the standard library's unit tests and the full compiler testsuite passes on Android/ARM.  Remaining work to be done is listed last.
+
All of the standard library's unit tests and the full compiler testsuite passes on Android/ARM.  Remaining work to be done is listed last.
  
 
==Prerequisites==
 
==Prerequisites==
Line 13: Line 13:
 
* Common development tools, such as CMake and git
 
* Common development tools, such as CMake and git
 
* ldc/druntime/phobos source
 
* ldc/druntime/phobos source
** Get the source using git, as these Android patches were tested on the master branch of each repository.
+
** Get the source using git, as these Android patches were tested on the release-1.3.x branch of each repository.
* llvm 3.9.1 source, either from the official release or git  
+
* llvm 4.0.1 source, either from the official release or git  
 
* Android native toolchain, [https://developer.android.com/ndk/index.html the NDK] and optionally [https://developer.android.com/studio/index.html the SDK]
 
* Android native toolchain, [https://developer.android.com/ndk/index.html the NDK] and optionally [https://developer.android.com/studio/index.html the SDK]
 
** The SDK is necessary if you want to package a GUI app; the NDK is enough if you just want to build a command-line binary, such as a test runner.  If you get the SDK, all that's needed is the "SDK Tools only" version, as long as you don't plan on using their IDE integration.  I will only write about using the command-line tools.  The SDK requires JDK 7: follow their instructions to make sure it's installed right.
 
** The SDK is necessary if you want to package a GUI app; the NDK is enough if you just want to build a command-line binary, such as a test runner.  If you get the SDK, all that's needed is the "SDK Tools only" version, as long as you don't plan on using their IDE integration.  I will only write about using the command-line tools.  The SDK requires JDK 7: follow their instructions to make sure it's installed right.
Line 33: Line 33:
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
 
cd ~
 
cd ~
curl -L -O http://downloads.dlang.org/releases/2.x/2.072.1/dmd_2.072.1-0_amd64.deb
+
curl -L -O http://downloads.dlang.org/releases/2.x/2.074.1/dmd_2.074.1-0_amd64.deb
sudo dpkg -i dmd_2.072.1-0_amd64.deb
+
sudo dpkg -i dmd_2.074.1-0_amd64.deb
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Line 40: Line 40:
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
 
sudo mkdir -p /opt/android-sdk/ndk-bundle
 
sudo mkdir -p /opt/android-sdk/ndk-bundle
curl -L -O https://dl.google.com/android/repository/android-ndk-r14b-linux-x86_64.zip
+
curl -L -O https://dl.google.com/android/repository/android-ndk-r15b-linux-x86_64.zip
sudo unzip android-ndk-r14b-linux-x86_64.zip 'android-ndk-r14b/*' -d /opt/android-sdk/ndk-bundle
+
sudo unzip android-ndk-r15b-linux-x86_64.zip 'android-ndk-r15b/*' -d /opt/android-sdk/ndk-bundle
export NDK=/opt/android-sdk/ndk-bundle/android-ndk-r14b
+
export NDK=/opt/android-sdk/ndk-bundle/android-ndk-r15b
 
</syntaxhighlight>
 
</syntaxhighlight>
  
As Windows Subsystem for Linux does not support USB you have to install Android SDK and Ant on your windows system and execute the commands "android" and "ant" from your DOS console.  
+
As Windows Subsystem for Linux does not support USB, you have to install Android SDK and Ant on your Windows system and execute the commands "android" and "ant" from your DOS console.  
  
 
==Compile llvm==
 
==Compile llvm==
  
Get the source for llvm, either [http://llvm.org/releases/download.html#3.9.1 the official 3.9.1 release] or [https://github.com/llvm-mirror/llvm a git repository, like this llvm mirror].  [https://gist.github.com/joakim-noah/1fb23fba1ba5b7e87e1a Download the patch for llvm], apply it, and then [http://llvm.org/docs/GettingStarted.html#getting-started-quickly-a-summary build llvm as you would normally], with the ARM target and for Android by default:
+
Get the source for llvm, either [http://llvm.org/releases/download.html#4.0.1 the official 4.0.1 release] or [https://github.com/llvm-mirror/llvm a git repository, like this llvm mirror].  [https://gist.github.com/joakim-noah/1fb23fba1ba5b7e87e1a Download the patch for llvm], apply it, and then [http://llvm.org/docs/GettingStarted.html#getting-started-quickly-a-summary build llvm as you would normally], with the ARM target, for Android by default, and leaving out tools and utilities you don't need:
  
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
curl -L -O http://releases.llvm.org/3.9.1/llvm-3.9.1.src.tar.xz
+
curl -L -O http://releases.llvm.org/4.0.1/llvm-4.0.1.src.tar.xz
tar xvf llvm-3.9.1.src.tar.xz
+
tar xvf llvm-4.0.1.src.tar.xz
cd llvm-3.9.1.src/
+
cd llvm-4.0.1.src/
 
curl -O https://gist.githubusercontent.com/joakim-noah/1fb23fba1ba5b7e87e1a/raw/ff54ecbe824b5f45669ea3a86f136ded16b1dd91/android_tls
 
curl -O https://gist.githubusercontent.com/joakim-noah/1fb23fba1ba5b7e87e1a/raw/ff54ecbe824b5f45669ea3a86f136ded16b1dd91/android_tls
 
git apply android_tls
 
git apply android_tls
Line 60: Line 60:
 
mkdir build
 
mkdir build
 
cd build/
 
cd build/
cmake .. -DCMAKE_BUILD_TYPE=Release -DLLVM_TARGETS_TO_BUILD=ARM -DLLVM_DEFAULT_TARGET_TRIPLE=armv7-none-linux-android
+
cmake .. -DCMAKE_BUILD_TYPE=Release -DLLVM_TARGETS_TO_BUILD=ARM -DLLVM_DEFAULT_TARGET_TRIPLE=armv7-none-linux-android -DLLVM_BUILD_TOOLS=OFF -DLLVM_BUILD_UTILS=OFF
make -j5
+
make all llvm-config -j5
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Line 72: Line 72:
 
git clone --recursive https://github.com/ldc-developers/ldc.git
 
git clone --recursive https://github.com/ldc-developers/ldc.git
 
cd ldc/
 
cd ldc/
 +
git checkout -b ldc13 origin/release-1.3.x
 
git submodule update
 
git submodule update
 
curl -O https://gist.githubusercontent.com/joakim-noah/d74af3cf1355492557a9c56ef1bf2636/raw/a0ac30302b5d7cc47049fb5ef88a87ec9afab824/ldc_1.3_android_arm
 
curl -O https://gist.githubusercontent.com/joakim-noah/d74af3cf1355492557a9c56ef1bf2636/raw/a0ac30302b5d7cc47049fb5ef88a87ec9afab824/ldc_1.3_android_arm
Line 79: Line 80:
 
cd build/
 
cd build/
 
export DMD=/path/to/your/dmd2/linux/bin64/dmd
 
export DMD=/path/to/your/dmd2/linux/bin64/dmd
export NDK=/path/to/your/android-ndk-r14b
+
export NDK=/path/to/your/android-ndk-r15b
cmake .. -DLLVM_CONFIG=../../llvm-3.9.1.src/build/bin/llvm-config
+
cmake .. -DLLVM_CONFIG=../../llvm-4.0.1.src/build/bin/llvm-config
 
make ldc2 -j5
 
make ldc2 -j5
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Download and apply [https://gist.github.com/joakim-noah/348edc378d47fb90e32708be19286a2e the patch for druntime] and [https://gist.github.com/joakim-noah/09a59bdd6e04dd2f3d3ad6e15573ad97 the patch for phobos] before building them:
+
Download and apply [https://gist.github.com/joakim-noah/09a59bdd6e04dd2f3d3ad6e15573ad97 a small patch for the standard library, phobos], before building the D runtime and stdlib:
  
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
cd ../runtime/druntime/
+
cd ../runtime/phobos/
curl -O https://gist.githubusercontent.com/joakim-noah/348edc378d47fb90e32708be19286a2e/raw/1a19264ff051907f489be7f02fad9ace089f4adb/druntime_1.3_ldc_arm
+
curl -O https://gist.githubusercontent.com/joakim-noah/09a59bdd6e04dd2f3d3ad6e15573ad97/raw/ba5bd391f1e9b669599c4d4939542512400ac934/phobos_1.3_ldc_arm
git apply druntime_1.3_ldc_arm
 
 
 
cd ../phobos/
 
curl -O https://gist.githubusercontent.com/joakim-noah/09a59bdd6e04dd2f3d3ad6e15573ad97/raw/58dfe70deece7d019b341030670922b0104d2569/phobos_1.3_ldc_arm
 
 
git apply phobos_1.3_ldc_arm
 
git apply phobos_1.3_ldc_arm
  
Line 109: Line 106:
  
 
$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-z,nocopyreloc
 
$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-z,nocopyreloc
--sysroot=$NDK/platforms/android-9/arch-arm -lgcc
+
--sysroot=$NDK/platforms/android-16/arch-arm -lgcc
 
-gcc-toolchain $NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64
 
-gcc-toolchain $NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64
 
-target armv7-none-linux-androideabi -no-canonical-prefixes -fuse-ld=bfd
 
-target armv7-none-linux-androideabi -no-canonical-prefixes -fuse-ld=bfd
Line 136: Line 133:
 
==Run the druntime and phobos unit tests==
 
==Run the druntime and phobos unit tests==
  
Go back to the linux shell and build the tests for druntime and phobos (don't add the -j5 flag to build in parallel unless you have gigabytes of memory available, as compiling some of the phobos modules' tests takes a fair amount of RAM):
+
Go back to the linux shell, apply [https://gist.github.com/joakim-noah/348edc378d47fb90e32708be19286a2e a patch for the test runner in druntime], and build the tests for druntime and phobos (don't add the -j5 flag to build in parallel unless you have gigabytes of memory available, as compiling some of the phobos modules' tests takes a fair amount of RAM):
  
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
 +
cd ../runtime/druntime/
 +
curl -O https://gist.githubusercontent.com/joakim-noah/348edc378d47fb90e32708be19286a2e/raw/2b473ff45ff4abc68852ebb1868354b8528026e0/druntime_1.3_ldc_arm
 +
git apply druntime_1.3_ldc_arm
 +
 +
cd ../../build/
 
make test-runner
 
make test-runner
 
</syntaxhighlight>
 
</syntaxhighlight>
Line 177: Line 179:
  
 
$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-soname,libnative-activity.so
 
$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-soname,libnative-activity.so
-shared --sysroot=$NDK/platforms/android-9/arch-arm main.o sensor.o
+
-shared --sysroot=$NDK/platforms/android-16/arch-arm main.o sensor.o
 
../../../ldc/build/lib/libphobos2-ldc.a ../../../ldc/build/lib/libdruntime-ldc.a
 
../../../ldc/build/lib/libphobos2-ldc.a ../../../ldc/build/lib/libdruntime-ldc.a
 
android_native_app_glue.o -lgcc
 
android_native_app_glue.o -lgcc
Line 186: Line 188:
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Package the app as the SDK directs.  I use the older Ant approach, which is being deprecated: replace it with the Gradle command from a newer SDK if neededFor Ant, set the path to your SDK, then run these commands:
+
Package the app as the SDK directs.  I document the older Ant approach, which is deprecated, replace it with the Gradle command from a newer SDK.  With Ant, set the path to your SDK, then run these commands:
  
 
<syntaxhighlight lang=bash>
 
<syntaxhighlight lang=bash>
Line 222: Line 224:
  
 
==Directions for future work==
 
==Directions for future work==
 
+
* You may notice that I added an empty main function in the D translation of the C sample app: that's a hack to build a shared library.  The linux shared library support in druntime's rt.sections_elf_shared may eventually be integrated with Android to get rid of that.
* Two modules, core.thread and std.parallelism, have tests that cause the test runner to hang when run from inside an apk as opposed to on the command line.  Trying to suspend a thread from another thread, either directly by calling thread_suspendAll() or indirectly when the GC runs a full collect on a multi-threaded app, fails, because pthread_kill doesn't return and hangs the calling thread.  It appears that this is related to using SIGUSR1/2 for suspending and resuming threads: [https://github.com/dlang/druntime/pull/1565 applying Ilya's patch to switch to real-time signals] works around this issue for now.
 
 
 
* You may notice that I added an empty main function in the D translation of the C sample app: that's a hack to build a shared library.  Some of the linux shared library support in druntime's rt.sections_elf_shared may eventually be integrated with Android to get rid of that.
 
  
 
* Now that we can write D code for Android, it'll make building easier if the D cross-compilers are integrated with a build tool, like [https://github.com/atilaneves/reggae reggae] or [http://jasonwhite.github.io/button/ Button].
 
* Now that we can write D code for Android, it'll make building easier if the D cross-compilers are integrated with a build tool, like [https://github.com/atilaneves/reggae reggae] or [http://jasonwhite.github.io/button/ Button].

Revision as of 10:21, 14 July 2017

This page will show you how to build an ldc cross-compiler for Android/ARM on linux or Windows 10 (by using the new bash on Ubuntu linux subsystem), along with how to build and run both the druntime/phobos tests and an Android D app using the cross-compiler. Prebuilt native and cross-compilers are available here.

All of the standard library's unit tests and the full compiler testsuite passes on Android/ARM. Remaining work to be done is listed last.

Prerequisites

  • linux/x64 shell, where you'll build and run ldc
    • You can use a virtual machine like VirtualBox/VMware, with at least 512 MB of memory and 1 GB of swap, particularly if building the phobos unit tests, and 10 GB of disk space.
    • Windows 10: You can alternately use Bash on Ubuntu on Windows (the Windows Subsystem for Linux)
  • C++ compiler and toolchain, to build a slightly patched llvm and parts of ldc
  • A pre-built D compiler for linux, as the ldc frontend is written in D.
  • Common development tools, such as CMake and git
  • ldc/druntime/phobos source
    • Get the source using git, as these Android patches were tested on the release-1.3.x branch of each repository.
  • llvm 4.0.1 source, either from the official release or git
  • Android native toolchain, the NDK and optionally the SDK
    • The SDK is necessary if you want to package a GUI app; the NDK is enough if you just want to build a command-line binary, such as a test runner. If you get the SDK, all that's needed is the "SDK Tools only" version, as long as you don't plan on using their IDE integration. I will only write about using the command-line tools. The SDK requires JDK 7: follow their instructions to make sure it's installed right.
  • Android/ARM, whether a device or emulator
    • The SDK comes with an emulator. I use actual hardware, so that's what I'll discuss.

Notes for Bash on Ubuntu on Windows

  • Necessary packages
sudo apt-get install build-essential
sudo apt-get install git
sudo apt-get install cmake
sudo apt-get install unzip
sudo apt-get install libconfig-dev
  • DMD Compiler
cd ~
curl -L -O http://downloads.dlang.org/releases/2.x/2.074.1/dmd_2.074.1-0_amd64.deb
sudo dpkg -i dmd_2.074.1-0_amd64.deb
  • Android Native Development Kit
sudo mkdir -p /opt/android-sdk/ndk-bundle
curl -L -O https://dl.google.com/android/repository/android-ndk-r15b-linux-x86_64.zip
sudo unzip android-ndk-r15b-linux-x86_64.zip 'android-ndk-r15b/*' -d /opt/android-sdk/ndk-bundle
export NDK=/opt/android-sdk/ndk-bundle/android-ndk-r15b

As Windows Subsystem for Linux does not support USB, you have to install Android SDK and Ant on your Windows system and execute the commands "android" and "ant" from your DOS console.

Compile llvm

Get the source for llvm, either the official 4.0.1 release or a git repository, like this llvm mirror. Download the patch for llvm, apply it, and then build llvm as you would normally, with the ARM target, for Android by default, and leaving out tools and utilities you don't need:

curl -L -O http://releases.llvm.org/4.0.1/llvm-4.0.1.src.tar.xz
tar xvf llvm-4.0.1.src.tar.xz
cd llvm-4.0.1.src/
curl -O https://gist.githubusercontent.com/joakim-noah/1fb23fba1ba5b7e87e1a/raw/ff54ecbe824b5f45669ea3a86f136ded16b1dd91/android_tls
git apply android_tls

mkdir build
cd build/
cmake .. -DCMAKE_BUILD_TYPE=Release -DLLVM_TARGETS_TO_BUILD=ARM -DLLVM_DEFAULT_TARGET_TRIPLE=armv7-none-linux-android -DLLVM_BUILD_TOOLS=OFF -DLLVM_BUILD_UTILS=OFF
make all llvm-config -j5

Build ldc for Android/ARM

Clone the ldc repository, apply the Android patch, set the DMD and NDK environment variables to the paths of your pre-built D compiler and NDK install, and build ldc as usual:

cd ../../
git clone --recursive https://github.com/ldc-developers/ldc.git
cd ldc/
git checkout -b ldc13 origin/release-1.3.x
git submodule update
curl -O https://gist.githubusercontent.com/joakim-noah/d74af3cf1355492557a9c56ef1bf2636/raw/a0ac30302b5d7cc47049fb5ef88a87ec9afab824/ldc_1.3_android_arm
git apply ldc_1.3_android_arm

mkdir build
cd build/
export DMD=/path/to/your/dmd2/linux/bin64/dmd
export NDK=/path/to/your/android-ndk-r15b
cmake .. -DLLVM_CONFIG=../../llvm-4.0.1.src/build/bin/llvm-config
make ldc2 -j5

Download and apply a small patch for the standard library, phobos, before building the D runtime and stdlib:

cd ../runtime/phobos/
curl -O https://gist.githubusercontent.com/joakim-noah/09a59bdd6e04dd2f3d3ad6e15573ad97/raw/ba5bd391f1e9b669599c4d4939542512400ac934/phobos_1.3_ldc_arm
git apply phobos_1.3_ldc_arm

cd ../../build/
make druntime-ldc phobos2-ldc -j5

More info about the Android/ARM patches can be found with their release.

Build a command-line executable

Now that we have a D cross-compiler and cross-compiled the standard library for Android/ARM, let's try building a small program, the classic Sieve of Eratosthenes single-core benchmark:

./bin/ldc2 -c ../tests/d2/dmd-testsuite/runnable/sieve.d

$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-z,nocopyreloc
--sysroot=$NDK/platforms/android-16/arch-arm -lgcc
-gcc-toolchain $NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64
-target armv7-none-linux-androideabi -no-canonical-prefixes -fuse-ld=bfd
-Wl,--fix-cortex-a8 -Wl,--no-undefined -Wl,-z,noexecstack -Wl,-z,relro
-Wl,-z,now -fPIE -pie -Wl,--export-dynamic -lc -lm sieve.o lib/libphobos2-ldc.a
lib/libdruntime-ldc.a -o sieve

The compiler and linker flags were taken from the output from running a NDK sample app's build scripts in verbose mode.

Run this program on an Android device or emulator. I've solely run on actual Android devices, with either a terminal or SSH server app. After installing one of those, copy the sieve program to the device, go to the app's local directory by typing 'cd' at its command-line, copy the program there, and run it:

cd
cp /sdcard/sieve .
./sieve foobar

The program requires an argument, which is ignored. If it runs correctly, you'll see the following output, saying it ran 10 times and found 1899 primes in the first 8191 integers:

10 iterations
1899 primes

Run the druntime and phobos unit tests

Go back to the linux shell, apply a patch for the test runner in druntime, and build the tests for druntime and phobos (don't add the -j5 flag to build in parallel unless you have gigabytes of memory available, as compiling some of the phobos modules' tests takes a fair amount of RAM):

cd ../runtime/druntime/
curl -O https://gist.githubusercontent.com/joakim-noah/348edc378d47fb90e32708be19286a2e/raw/2b473ff45ff4abc68852ebb1868354b8528026e0/druntime_1.3_ldc_arm
git apply druntime_1.3_ldc_arm

cd ../../build/
make test-runner

Copy the test-runner and this list of druntime and phobos modules to your device and run it. I use the SSH server app on a random port, here's what I'd do (replace 192.168.35.7 with the IP address of your device and 20345 with the port you configured for the SSH service):

scp -P20345 test.list runtime/test-runner jo@192.168.35.7:
ssh -p20345 jo@192.168.35.7
./test-runner

The tests take about 25 seconds to run on my quad-core tablet: all should pass. One module, core.sync.semaphore, will need to be removed from the list of modules for any Android older than 6.0, because sem_destroy used to work differently in bionic.

Build a sample OpenGL Android app ported to D

Clone my android repository, which contains several headers and sample OpenGL apps from the NDK, translated to D:

cd ../../
git clone https://github.com/joakim-noah/android.git

You can find more info about building using the NDK in my earlier instructions for Android/x86. This is just the essence, redone for ARM. You will build a purely native D apk without any Java source.

Go to the native-activity sample app, compile the D source, then link the objects into a shared library and place it in the directory that the SDK expects:

cd android/samples/native-activity/

../../../ldc/build/bin/ldc2 -I../../ -c jni/main.d

../../../ldc/build/bin/ldc2 -I../../ -c ../../android/sensor.d

../../../ldc/build/bin/ldc2 -I../../ -c ../../android_native_app_glue.d

mkdir -p libs/armeabi-v7a/

$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin/clang -Wl,-soname,libnative-activity.so
-shared --sysroot=$NDK/platforms/android-16/arch-arm main.o sensor.o
../../../ldc/build/lib/libphobos2-ldc.a ../../../ldc/build/lib/libdruntime-ldc.a
android_native_app_glue.o -lgcc
-gcc-toolchain $NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64
-no-canonical-prefixes -fuse-ld=bfd -target armv7-none-linux-androideabi
-Wl,--fix-cortex-a8 -Wl,--no-undefined -Wl,-z,noexecstack -Wl,-z,relro -Wl,-z,now
-llog -landroid -lEGL -lGLESv1_CM -lc -lm -o libs/armeabi-v7a/libnative-activity.so

Package the app as the SDK directs. I document the older Ant approach, which is deprecated, replace it with the Gradle command from a newer SDK. With Ant, set the path to your SDK, then run these commands:

export SDK=/path/to/your/android-sdk-linux
$SDK/tools/android update project -p . -s --target 1
ant debug

Transfer the resulting bin/NativeActivity-debug.apk to your device, go to Settings->Security and allow installation of apps from unknown sources, ie from outside the Play Store, then install it. Go to your app folder and run the app named NativeActivity: it'll show a black screen initially, then flashes a bunch of colors when touched.

Run the druntime and phobos unit tests in an apk

Create the libs/armeabi-v7a/ directory as shown in the last section, then download and apply the small patch to have the sample app invoke the test runner, and rebuild:

curl -O https://gist.githubusercontent.com/joakim-noah/8ba3cd4958266f357295/raw/a52fcf1e63715f8b1bd3527afaa85872087b0f30/native_ldc_arm
git apply native_ldc_arm

cd ../../../ldc/build/
make test-runner-apk

This assumes that the ldc and android repositories are in the same directory, as shown in these instructions. If not, modify ANDROID_DIR in the CMake build script to use the path you want.

Finally, package the test runner apk:

cd ../../android/samples/native-activity/
ant debug

Transfer the resulting bin/NativeActivity-debug.apk to your device, and install it as before. Also, copy the list of modules to test to the /sdcard/ directory. The app will append its results to /sdcard/test.log, so if you happen to have a file with that name, move it.

This time, it should show a black screen for about a minute, while all the tests run. A touch after that and it should start flashing a bunch of colors. If not, look at the output in /sdcard/test.log and check if the app hung after any particular tested module. You can remove that module from test.list and try running again.

Directions for future work

  • You may notice that I added an empty main function in the D translation of the C sample app: that's a hack to build a shared library. The linux shared library support in druntime's rt.sections_elf_shared may eventually be integrated with Android to get rid of that.
  • Now that we can write D code for Android, it'll make building easier if the D cross-compilers are integrated with a build tool, like reggae or Button.