< expLog

Building a binary for Android

Often enough, I'd like to write and run some simple native code on my phone as a test. The simplest way is to just create a new project with Android Studio, but that occasionally seems a bit too heavy for my purposes.

This post describes a reasonably simple alternative that's not tied to a specific IDE, running gradle or forcibly deploying an appliction (except for Android N+).

Assuming that $PROJECT is the parent directory.

$PROJECT/jni/Android.mk - documentation

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_CFLAGS += -Wall

LOCAL_LDLIBS := -llog -g

LOCAL_C_INCLUDES := bionic

# Name the binary
LOCAL_MODULE := somebinary

# List out source files here
LOCAL_SRC_FILES := ../main.c

include $(BUILD_EXECUTABLE)

$PROJECT/jni/Application.mk - documentation

APP_MODULES := somebinary
APP_OPTIM := release
APP_PLATFORM := android-15
APP_PIE := true
APP_ABI := armeabi-v7a

$PROJECT/main.c

#include <stdio.h>

int main(int argv, char** argc) {
  printf("Hello, Android!");
  return 0;
}

(Optional) $PROJECT/run.sh

I like to have a simple shell file that I can trigger to execute the app for me - which I use as the emacs M-x compile command.

#!/bin/zsh
set -e

alias adb=/opt/android_sdk/platform-tools/adb

echo "Building..."
/opt/android_ndk/android-ndk-r13b/ndk-build

echo "Push..."
adb push libs/armeabi-v7a/somebinary /data/local/tmp/

echo "Run...\n"
adb shell /data/local/tmp/somebinary

ndk-build - documentation

This is a helpful wrapper script that runs the appropriate cross compilers, greatly simplifying the makefiles here. The only annoying side effect is the need to store everything in a jni folder, which I'm sure is configurable in a way I haven't quite found yet.