Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Cross compiling a C program for android

Tags:

c

android

arm

elf

I am trying to copy an executable from my Linux machine (Ubuntu) to an Android app as an asset. I was successfully able to move the executable over to the Android file system but when I try to execute I am presented with the error 'sh: not executable: 64-bit ELF file.' I ran the file command on the executable and this is was the output:

'ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so, for GNU/Linux 2.6.32 not stripped.'

When I run file on an executable that works on the Android Device:

'ELF 64-bit LSB executable, ARM aarch64, version 1 (SYSV), dynamically linked, interpreter /system/bin/linker64, stripped.'

To add a little bit of context I'm trying to compile this program.

I downloaded the Android NDK and I run the following commands to compile the program:

 sudo ./configure --cc=/home/username/arm/bin/arm-linux-androideabi-gcc 
 sudo make

The compilation works until it gets to linking then it spits out these errors:

/home/username/arm/bin/../lib/gcc/arm-Linux-androideabi/4.9.x/../../../../arm-Linux-androideabi/bin/ld: error: fio.o: incompatible target               
/home/username/arm/bin/../sysroot/usr/lib/crtbegin_dynamic.o:crtbrand.c:function _start: error: undefined reference to 'main'    
engines/net.c:318: error: undefined reference to 'inet_network'  
engines/net.c:322: error: undefined reference to 'inet_network'  
engines/net.c:323: error: undefined reference to 'inet_network'  
engines/net.c:318: error: undefined reference to 'inet_network'  
cgroup.c:28: error: undefined reference to 'setmntent'  
cgroup.c:34: error: undefined reference to 'getmntent_r'  
cgroup.c:45: error: undefined reference to 'endmntent'  
collect2: error: ld return 1 exit status  
Makefile:433: recipe for target 'fio' failed  
make *** [fio] Error 1

Do I need to specify a certain linker?

like image 930
Melvin Bosnjak Avatar asked Nov 28 '25 19:11

Melvin Bosnjak


1 Answers

I can't provide a complete answer for this, but hopefully the following helps.

You've correctly identified that your first binary was compiled for the wrong architecture (x86-64 vs ARM aarch64). The solution is to use a cross-compiler, like you have with arm-linux-androideabi-gcc.

To solve the "undefined reference" errors you also have to link against the cross-compiled versions of the libraries that supply those symbols. The -L flag can be used to point to the compiled libraries. You'll have to find the paths to those on your own.

For Android, the C standard library is provided by a library called Bionic. https://android.googlesource.com/platform/bionic/

I don't have any experience with the NDK, so I don't know if it comes with Bionic or not. I think the NDK is only intended for using C/C++ from within Java apps. It might not be sufficient for building standalone native programs.

I can highly recommend "Embedded Android" by Karim Yaghmour for more information on compiling the Android OS and adding native applications to the build. If you have an entire AOSP build system (it's huge), then that book will help you add your desired native program to your build. From there you can sideload the program to a device.

like image 85
remcycles Avatar answered Dec 01 '25 10:12

remcycles