Last active
August 29, 2015 14:00
-
-
Save gnail737/9ad7fc93142513398889 to your computer and use it in GitHub Desktop.
My test code to run native ARM C binaries on Android
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| /******************************************************************************************************************* | |
| To use the following code you need to create a Java based android Project and cross-compile a test C executable on Linux/PC/Mac | |
| and Copy it to Asset Folder of your Android Project. Instruction on Cross-Compile can be found in | |
| http://www.kandroid.org/ndk/docs/STANDALONE-TOOLCHAIN.html | |
| and | |
| http://www.ikravets.com/computer-life/programming/2014/01/18/an-android-cross-compiling-environment-on-windowsunix-like-systems-using-ndk | |
| The code used to run binary and fetch output from stdout is copied from stackoverflow post - | |
| http://stackoverflow.com/questions/4703131/is-it-possible-to-run-a-native-arm-binary-on-a-non-rooted-android-phone | |
| and | |
| http://gimite.net/en/index.php?Run%20native%20executable%20in%20Android%20App | |
| http://kevinboone.net/android_native.html | |
| ********************************************************************************************************************/ | |
| package com.example.hellonativecode; | |
| import java.io.BufferedReader; | |
| import java.io.FileOutputStream; | |
| import java.io.IOException; | |
| import java.io.InputStream; | |
| import java.io.InputStreamReader; | |
| import android.app.Activity; | |
| import android.content.Context; | |
| import android.os.Bundle; | |
| import android.os.Handler; | |
| import android.os.Looper; | |
| import android.os.Message; | |
| import android.util.Log; | |
| import android.widget.TextView; | |
| public class MainActivity extends Activity { | |
| /** Called when the activity is first created. */ | |
| static final String TAG = "com.example.hellonativecode.MainActivity"; | |
| static final String exeFileName = "hello"; | |
| static String nativePath = ""; | |
| NativeWorker nw; | |
| TextView tv; | |
| @Override | |
| public void onCreate(Bundle savedInstanceState) | |
| { | |
| super.onCreate(savedInstanceState); | |
| /* Create a TextView and set its content. | |
| */ | |
| copyFile(exeFileName, nativePath, this, true); | |
| tv = new TextView(this); | |
| nw = new NativeWorker(); | |
| nw.start(); | |
| setContentView(tv); | |
| } | |
| private static void copyFile(String assetPath, String localPath, Context context, boolean doCopy) { | |
| try { | |
| InputStream in = context.getAssets().open(assetPath); | |
| //FileOutputStream out = new FileOutputStream(localPath); | |
| FileOutputStream out = context.openFileOutput(assetPath, Context.MODE_PRIVATE); | |
| nativePath = context.getFilesDir()+"/"+assetPath; | |
| int read; | |
| if (doCopy) { | |
| byte[] buffer = new byte[4096]; | |
| while ((read = in.read(buffer)) > 0) { | |
| out.write(buffer, 0, read); | |
| } | |
| } | |
| out.close(); | |
| in.close(); | |
| } catch (IOException e) { | |
| throw new RuntimeException(e); | |
| } | |
| } | |
| class NativeWorker extends Thread { | |
| @Override | |
| public void run() { | |
| final StringBuffer output = new StringBuffer(); | |
| Process nativeApp = null; | |
| try { | |
| nativeApp = Runtime.getRuntime().exec("/system/bin/chmod 777 "+nativePath); | |
| nativeApp.waitFor(); | |
| Thread.sleep(2000); | |
| nativeApp = Runtime.getRuntime().exec(nativePath); | |
| } catch (IOException e) { | |
| Log.i(TAG, "Binary with name " + nativePath + " not found!!!"); | |
| e.printStackTrace(); | |
| } catch (InterruptedException e) { | |
| // TODO Auto-generated catch block | |
| e.printStackTrace(); | |
| } | |
| if (nativeApp != null) { | |
| BufferedReader reader = new BufferedReader(new InputStreamReader(nativeApp.getInputStream())); | |
| int read; | |
| char[] buffer = new char[4096]; | |
| //output = new StringBuffer(); | |
| try { | |
| while ((read = reader.read(buffer)) > 0) { | |
| output.append(buffer, 0, read); | |
| } | |
| reader.close(); | |
| // Waits for the command to finish. | |
| nativeApp.waitFor(); | |
| } catch (IOException e) { | |
| e.printStackTrace(); | |
| } catch (InterruptedException e) { | |
| Log.e(TAG, "Our spawned Process is Interrupted !!"); | |
| e.printStackTrace(); | |
| } | |
| String nativeOutput = output.toString(); | |
| Log.e(TAG, "here is the result : "+nativeOutput); | |
| } | |
| //run this at the end to signal mainthread our processing is done | |
| boolean hdl = new Handler(Looper.getMainLooper(), new Handler.Callback() { | |
| @Override | |
| public boolean handleMessage(Message msg) { | |
| tv.setText(new String(output)); | |
| return true; | |
| } | |
| }).sendEmptyMessage(0); | |
| } | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment