想编译原生Android二进制文件,我可以在手机终端上运行

想编译原生Android二进制文件,我可以在手机终端上运行,android,c,gcc,android-ndk,arm,Android,C,Gcc,Android Ndk,Arm,几天来,我一直在尝试编译一个本地ARM Android二进制文件,它将使用终端应用程序在我的手机上执行。我想生成与手机上安装的标准Posix二进制文件相同类型的二进制文件,如ls、mkdir等。我已经在Mac OS X下下载了Android NDK,并且能够编译简单的ELF二进制文件,没有错误。然而,当我把它们转接到手机上时,它们总是有故障。也就是说,当在GCC中使用-static编译时,它们会出错。如果我不使用-static,它们会抱怨没有链接,等等。简单地说,它们不工作 我的假设是,它们没有

几天来,我一直在尝试编译一个本地ARM Android二进制文件,它将使用终端应用程序在我的手机上执行。我想生成与手机上安装的标准Posix二进制文件相同类型的二进制文件,如ls、mkdir等。我已经在Mac OS X下下载了Android NDK,并且能够编译简单的ELF二进制文件,没有错误。然而,当我把它们转接到手机上时,它们总是有故障。也就是说,当在GCC中使用-static编译时,它们会出错。如果我不使用-static,它们会抱怨没有链接,等等。简单地说,它们不工作

我的假设是,它们没有正确地链接到Android标准C库。即使我将我的二进制文件与NDK提供的libc链接,它们仍然不起作用。我读到安卓使用仿生C库,并试图下载其源代码,但我不确定如何从中构建库(似乎都是ARM组装)

手机上的安卓C库与安卓NDK提供的库不同,这是真的吗?NDK中包含的一个是否允许我编译可以通过终端执行的本机二进制文件?非常感谢您的指导

更新:

我最终在MacOSX上使用GCC4.7.0实现了这一点。我下载了仿生头文件,然后使用Android NDK附带的C库编译了一个动态链接的二进制文件。我能够使用手机的C库(二进制为33K)在手机上运行一个测试应用程序。我还尝试静态链接NDK的C库,这也很有效

为了让这一切正常工作,我必须将-nostlib传递给GCC,然后手动将crtbegin_dynamic.o和crtend_android.o添加到GCC的命令行中。它的工作原理如下:

$CC \
$NDK_PATH/usr/lib/crtbegin_dynamic.o \
hello.c -o hello \
$CFLAGS \
$NDK_PATH/usr/lib/crtend_android.o
对于静态二进制文件,请使用“crtbegin_static.o”。这在crtbegin_dynamic.S/crtbegin_static.S源代码中有说明


对于这个实验,我只使用了普通的'OLGCC4.7.0和Binutils2.22。我还使用newlib编译了GCC,但实际上我并没有将我的ARM二进制文件与newlib链接起来。我正在强迫GCC/ld直接链接到Android NDK提供的libc,或者如果是动态二进制文件,则直接链接到手机上的libc。

如果博客中提到的可以帮助您,请尝试。根据博文,你想使用仿生库,但手机上已经安装了仿生库,而不是单独编译的版本。

使用CMake和Android NDK是编译Android控制台应用程序的好方法

下载并安装。如果程序名为main.c,则在文件
CMakeLists.txt
中编写以下内容:

project(test)
cmake_minimum_required(VERSION 2.8)
add_executable(test ./main.c)
然后运行
cmake-DCMAKE\u TOOLCHAIN\u FILE=$ANDTOOLCHAIN.


然后,您将为您的程序创建一个Makefile,您可以运行
make
以使您的
test
可执行。

只需使用android ndk即可。然后像这样构建一个Android.mk。
include$(BUILD\u EXECUTABLE)
告诉它构建一个可执行文件而不是JNI.lib

Android.mk
首先,确保您拥有NDK:

以下是为您的手机编译C二进制文件的最简单方法:

通常$NDK(可能不同)=

Linux:

/主页/
/android ndk

Mac OS X:

/用户/
/android ndk

在终端:

# create tool-chain - one line
# New method in ndk 12.
$NDK/build/tools/make_standalone_toolchain.py --arch arm --install-dir=/tmp/my-android-toolchain
# Old method.
#$NDK/build/tools/make-standalone-toolchain.sh --platform=android-3 --install-dir=/tmp/my-android-toolchain

# add to terminal PATH variable
export PATH=/tmp/my-android-toolchain/bin:$PATH

# make alias CC be the new gcc binary
export CC=arm-linux-androideabi-gcc

# compile your C code(I tried hello world)
$CC -o foo.o -c foo.c

# push binary to phone
adb push foo.o /data/local/tmp

# execute binary
adb /data/local/tmp/foo.o

为什么在这种情况下使用Crystax而不是官方的NDK?没有特别的原因,有时在实验和学习时尝试不同的东西会有所帮助。这就是为什么我只是做了一个评论。仅供参考,如果你设置一个构建,就好像你正在创建一个jni库(见NDK发行版中的示例),并将Android.mk中的build\u SHARED\u库更改为build\u EXECUTABLE,你将得到一个可执行文件,尽管这是一个非官方的(可能会消失,等等)ndk构建系统的功能。这可能是我的解决方案。我一直在修补agcc,但没有成功。这似乎利用了android构建系统的优势。。。有没有关于它是如何在某处工作的解释?谢谢$(NDK_ROOT)/docs/ANDROID-MK.html描述了所有宏是什么。还有一个额外的
endif
@SonicBison-所以我成功地编译了二进制文件。现在有没有具体的地方我们应该把二进制文件放在哪里?我的设备是根。如果我对777执行CHMOD,它的行为是否会像SU一样,并获得系统应用程序的访问权限,比如INEJCT_事件权限。基本上我想在一天结束时调用injectEvents?@myCodeHurts你不应该把它放在SD卡上,因为它不允许从那里执行任何东西……你在那里执行对象文件吗?没有链接?真的有用吗?是的,看起来不错。我很可能需要删除
-c
。这是我不久前写的。
# create tool-chain - one line
# New method in ndk 12.
$NDK/build/tools/make_standalone_toolchain.py --arch arm --install-dir=/tmp/my-android-toolchain
# Old method.
#$NDK/build/tools/make-standalone-toolchain.sh --platform=android-3 --install-dir=/tmp/my-android-toolchain

# add to terminal PATH variable
export PATH=/tmp/my-android-toolchain/bin:$PATH

# make alias CC be the new gcc binary
export CC=arm-linux-androideabi-gcc

# compile your C code(I tried hello world)
$CC -o foo.o -c foo.c

# push binary to phone
adb push foo.o /data/local/tmp

# execute binary
adb /data/local/tmp/foo.o