Android build system就是编译系统的意思
在我们需要向自己编译的源代码中增加模块的时候,需要一些规则,当然这个规则都是类似的。
Android.mk文件解析
让我们来看一个
Android.mk
文件的样子
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE :=Hello
LOCAL_SRC_FILES := hello.c
include $(BUILD_SHARED_LIBRARY)
①
LOCAL_PATH :=$(call my-dir)
固定写法,
LOCAL_PATH
表示此时位于工程目录的根目录中,
(call my-dir)
的功能由编译器提供,被用来返回当前目录的地址(包含
Android.mk
本身)
②
include $(CLEAR_VARS)
固定写法,
CLEAR_VARS
这个变量由编译系统提供,并且要执行一个
GNU makefile
文件,这个功能会清理掉所有以
LOCAL_
开头的内容(比如
LOCAL_MODULE
、
LOCAL_SRC_FILES
等),除了
LOCAL_PATH
。这句话也是必须的,因为如果所有变量都是全局变量的话,所有的可控的编译文件都需要在一个单独的
GNU
中被解析并执行
③
LOCAL_MODULE :=Hello
LOCAL_MODLE
变量必须被定义,用来区分
Android.mk
中的每一个模块。文件名必须是唯一的,不能有空格。注意,编译器会为你自动加上一些前缀和后缀,来保证文件是一致的。比如:这里表明一个动态链接库模块被命名为“
Hello
”,但是最后会生成“
libHello.so
”文件。但是在
java
中装载这个库的时候还要使用“
Hello
”名称。
④
LOCAL_SRC_FILES :=hello.c
LOCAL_SRC_FILES
变量必须包含一个
C
和
C++
源文件的列表,这些会被编译并聚合到一个模块中
注意:这里并不需要列头文件和被包含的文件,因为编译系统会自动为你计算相关的属性,源代码的列表会直接传递给编译器
⑤
include $(BUILD_SHARED_LIBRARY)
BUILD_SHARED_LIBRARY
这个变量由系统提供,并且指定给
GNU makefile
的脚本,它可以收集所有你定义的
”include $(CLEAR_VARS)”
中以
LOCAL_
开头的变量,并且决定哪些要编译,哪些应该做的更加准确。我们同样可以使用
BUILD_STATIC_LIBRARY
来生成一个静态库,如果使用
BUILD_STATIC_LIBRARY
编译系统便会生成一个以“
lib$(LOCAL_MODULE).a
”为文件名的文件来提供动态库的调用
⑥
TARGET_ARCH
TARGET_ARCH
是指架构中
CPU
的名字已经被
Android
开源代码明确指出了,这里的
arm
包含了任何
ARM-
独立结构的架构,以及每个独立的
CPU
版本
⑦
TARGET_PLATFORM
Android
平台的名字在
Android.mk
文件中被解析,比如
”android-2.3”
⑧
TARGET_ROOT_OUT
:表示根文件系统
用法:
CAL_MODULE_PATH:=$(TARGET_ROOT_OUT)
⑨
TARGET_OUT:
表示
system
文件系统
⑩
TARGET_OUT_DATA:
表示
data
文件系统
⑪
TARGET_ABI
TARGET_ABI
平台目标板和
abi
的链接,这里要定义
$(TARGET_PLATFORM)-$(TARGET_ARCH_ABI)
,它们都非常有用,特变是当你想测试一个具体的系统镜像在几个真实设备的时候
下面是
GNU
编译出来的宏,并且它们都必须使用“
$(call <function>)
”才能返回文字化的信息。
all-subdir-makefiles
:返回一个
Android.mk
文件所在位置的列表,以及当前
my-dir
的路径。
比如:
include $(call all-subdir-makefiles)
this-makefile
:返回当前
makefile
的路径(就是哪个功能被调用了)
parent-makefile
:返回
makefile
的包含树,也就是包含
makefile
的当前文件
Application.mk
要讲
C\C++
编译为
so
文件,光有
Android.mk
文件是不行的,还需要
Application.mk
文件。
Application.mk
文件存放的位置是
NDK
工程的根目录,
Application.mk
文件就是用来描述应用程序中所需要的原生的模块(也就是静态库和动态库),每一个
Application.mk
文件都必须放在应用目录下的子目录,例如
$NDK/apps/HelloNdk/Application.mk
,作为
GNU makefile
的一部分,
Application.mk
文件必须要定义以下部分
1、
APP_MODULES
APP_MODULES
变量是强制性的,并且会列出所有你所需要的模块(通过
Android.mk
)
2、
APP_PROJECT_PATH
APP_PROJECT_PATH
变量也是强制性的,并且会给出应用程序工程的根目录一个绝对路径。这是用来复制或者安装一个没有任何版本限制的
JNI
库,从而给
APK
生成工具一个详细的路径。
例如:
\HelloNDK\Application.mk
APP_PROJECT_PATH := $(call my-dir)/project
APP_MODULES := HelloNdk
这里定义了工程路径为
$(call my-dir)/project
,而要编译的模块则是
HelloNdk
,这样编译系统才会找到我们要编译的库和原文件
3、
APP_CFLAGS
则是当要编译模块中有任何
C
文件的时候,
C
编译器的信号就会被发出
4、
APP_OPTIM
这个变量是可选的,可以定义为发布版或者测试版
------------------------------------------------------------------------------------------------------------------------
在Android.mk中:
include $(BUILD_EXECUTABLE)表示生成二进制可执行文件
include $(BUILD_STATIC_LIBRARY)表示生成静态库.a文件,名字叫做lib<工程名>.a
include $(BUILD_SHARED_LIBRARY)表示生成动态库.so文件,名字叫做lib<工程名>.so
另外需要注意的是,生成的文件需要放在手机的data/local目录下,才可以有执行的权限(未root),如果root了,则会有些目录是可以执行,但是某些目录依然不能执行,当然可以用umount命令解决。SD卡是没有执行权限的,所以当你生成的比如二进制可执行文件放到sdcard中时,是无法运行的。
可以这样测试一下哪些是有执行权限,哪些是没有的:
*将手机插入电脑,并打开USB调试
*在终端输入adb shell进入
*su(root了的手机)
*mount:可以看到一大堆的列表,如果对应的目录的信息中有noexec,说明这个目录就没有执行权限,剩下的都可以执行二进制等文件。
Android.mk文件的具体语法参见我的博客:http://hualang.iteye.com/blog/1140414
向Android源代码中增加模块主要有如下几种:
1、增加可执行文件
增加可执行文件,这些可执行文件一般都是由C/C++生成,下面简单的介绍一些如何向源代码中生成可执行文件
假设我的源代码在~/mydroid目录下
在external/loulijun/test目录下,创建两个文件,一个C,一个Android.mk
hello.c
#include <stdio.h>
int main(void)
{
printf("Hello world!\n");
return 0;
}
Android.mk
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES :=hello.c
LOCAL_MODULE_TAGS :=optional
LOCAL_MODULE :=test
include $(BUILD_EXECUTABLE)
首先退出到mydroid目录下,执行
. build/envsetup.sh
或者
source build/envsetup.sh
进行环境变量的配置
然后进入到test目录下,执行“mm”(mm表示编译当前项目),如果想重新执行,可以"mm -B"
这样,会在out/target/product/generic/obj/EXECUTABLES/test_intermediates/LINKED/目录下生成可执行文件test
然后将test文件用adb push test /data/local 到data/local目录下。
下面开始执行,你可以在手机中用terminal emulator来执行,也可以以adb shell后,执行
./test
显示:Hello world!
2、增加静态库(.a)
Android.mk文件
LOCAL_PATH :=$(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES := \
hello.c
LOCAL_MODULE :=test
include $(BUILD_STATIC_LIBRARY)
编译:
mydroid#. build/envsetup.sh
test#mm
生成的结果在out/target/product/generic/obj/STATIC_LIBRARY
目标文件夹{XXX}_static_intermediates下,XXX为你定义的模块名称test
假如这个静态库是由hello.c生成的,但是生成的静态库是不能直接使用的,而是由动态库调用它
3、增加动态库(.so)
编译动态库其实可以用NDK的,那样生成非常方便,但是有时候还是需要掌握其他的方法的
Android.mk
LOCAL_PATH :=$(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES := \
hello.c
LOCAL_MODULE :=test
include $(BUILD_SHARED_LIBRARY)
编译的放法都差不多,只不过Android.mk不同的是最后一句,如果比较一下就会发现那句话决定了生成的是什么
不过要想生成动态库,绝非是这么简单的,有时候只需要Android.mk和源文件即可,但是有时候还需要Application.mk文件。Application.mk文件的具体语法很快会在博客中更新
下面是使用
NDK
来生成
.so
文件的,环境是在
ubuntu11.04
下面
1、
下载
Android-NDK-r6
,将其解压到
~/android/android-ndk-r6
目录下
2、
配置
.bash_profile
文件,加入
NDK=~/android/android-ndk-r6
export NDK
3、
cd $NDK
后,进入
ndk
的目录,我以它自带的项目为例,进入
samples/hello-jni
在终端输入
$NDK/ndk-build
系统会自动编译这个文件,并将生成的
libhello-jni.so
文件存放在当前目录的
libs/armeabi
目录下
4、
我们可以将这个生成的
libhello-jni.so
放在
Android
源代码的适当的位置即可使用了
下面是相应的文件
hello-jni.c
#include <string.h>
#include <jni.h>
jstring
Java_com_example_hellojni_HelloJni_stringFromJNI( JNIEnv* env,
jobject thiz )
{
return (*env)->NewStringUTF(env, "Hello from JNI !");
}
Android.mk
文件
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := hello-jni
LOCAL_SRC_FILES := hello-jni.c
include $(BUILD_SHARED_LIBRARY)
由于这里只是使用了一个简单的
C
文件,所以没用用到
Application.mk
文件
然后将
hello-jni
导入到
eclipse
中,运行模拟器,即可显示
下面再看一个例子
native-activity
1、
进入目录后执行
$NDK/ndk-build
2、
生成
libnative_activity.so
并存于当前目录的
lib/armeabi
目录下,另外由源代码生成的还有静态库,存放于
obj/local/armeabi/ libandroid_native_app_glue.a
这里,由于
main.c
比较大,就不贴上了
Android.mk
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := native-activity
LOCAL_SRC_FILES := main.c
LOCAL_LDLIBS := -llog -landroid -lEGL -lGLESv1_CM
LOCAL_STATIC_LIBRARIES := android_native_app_glue
include $(BUILD_SHARED_LIBRARY)
$(call import-module,android/native_app_glue)
Application.mk
APP_PLATFORM := android-10
运行结果:颜色会逐渐变浅,然后再次从这个颜色变浅
4、增加apk文件(有源代码)
如果将
android
程序的源代码加入到
build
system
中呢
(1)
在
eclipse
开发环境中创建你的
android
工程,比如叫做
Success
(2)
将工程拷贝到源代码的
package/apps
目录下
(3)
进入
Success
目录下,创建一个
Android.mk
文件,内容如下
LOCAL_PATH :=$(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE_TAGS :=optional
LOCAL_SRC_FILES :=$(call all-java-files-under, src)
LOCAL_PACKAGE_NAME :=(工程名字)
LOCAL_CERTIFICATE :=platform
include $(BUILD_PACKAGE)
(4)
退回到
android
源代码目录下,执行
#. build/envsetup.sh
#mmm packages/apps/Success
编译成功之后,会在
out/target/product/generic/system/app/Success.apk
(5)
如果要在真机上测试,
system
的目录是在
out/target/product/crespo
目录下,编译的时候需要设置一些参数。为了测试,将
crespo
中的
system
记其他内核等文件放入到一个叫做
samsung
的文件夹中,再将
Success.apk
放到
system/app
中
(6)
用
#zip –r update.zip .
命令将其打包为
zip
,也可以用
zip
直接压缩
(7)
用
#java –jar testsign.jar Samsung/update.zip update.zip
将
zip
包签名
(8)
打开手机的
usb
调试,连接到电脑上,在终端输入
#adb push update.zip /sdcard/update.zip
,将
zip
包上传到设备的
sdcard
目录下
(9)
输入
#adb reboot bootloader
进入
bootloader
界面
(10)
输入
#fastboot flash recovery recovery.img
刷
recovery,
我刷的是
Recovery
3.0
(11)
进入
Recovery
选项,刷机,重启后就可以见到
Success.apk
程序了
注意:修改
AndroidManifest.xml
,在
manifest
标签中加入
android:sharedUserId=”media”
,当然这个
media
只是个
id
,它的名字随便一般类似包名。我们知道,在不同的
apk
包中默认是不能相互访问数据的,但是如果在
AndroidManifest.xml
中设置
sharedUserId
并且相同的话,那么这两个包就可以相互访问数据。由于我写的只是个测试程序,所以没有加入这条
5、增加apk文件(无源代码)
(1)
这种方式最简单,就是将
***.apk
文件拷贝到编译
android
源代码时候生成的
out/target/product/crespo/system/app
中,执行
make snod
后就可以把
apk
添加到
system.img
中了,然后将
system
目录及其他的几个文件打包成
zip
并签名后即可,刷机后可以看到这个内置的系统程序。
(2)
上一种方式在
make clean
之后,再次
make
以后才能执行上述的操作,比较麻烦
①
新建一个目录,在
packages/apps
下面,专门用来存放
apk
文件
#mkdir packages/apps/apks
#cd packages/apps/apks
在这个目录中新建一个
Android.mk
文件
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_POST_PROCESS_COMMAND := (shell cp –r $(LOCAL_PATH)/*.apk
$(TARGET_OUT)/app/)
保存退出
②
把需要编译的
apk
拷贝到
apks
目录中,执行
make
,在
apks
中的
apk
就会被拷贝到
out/target/product/generic/system/app
中
③
执行
make snod
即可
这样,在执行
make clean
之后,再次
make
,只需要
make snod
即可了
- 大小: 6 KB
- 大小: 5.7 KB
分享到:
相关推荐
NULL 博文链接:https://hualang.iteye.com/blog/1132207
Rom助手-Android ROM工具15.1版-支持精简
dsixda's Android Kitchen Compatible with Windows (Cygwin) / Linux / Mac OS X Introduction This is a tool for those who want to start learning how to make custom ROMs, or who just want to save some ...
我的老设备三星N8000安装APP总是提示包解析错误,究其原因还是系统Android版本太老旧(安卓4.1.2)。 最近把三星N8000升级成了Android 11,用网站( https://androidfilehost.com )提供的基于Android 11的ROM...
Android10-system.img-unpack EMUI10 MIUI12 Flyme8 firmware unpack. Android system.img unpack repack on Windows10. Android 8以上 ROM解包工具 文件说明: 1.brotli:解压工具,用于将「system.new.dat.br」...
Android 8以上 ROM解包工具 文件说明: 1.brotli:解压工具,用于将「system.new.dat.br」文件解压为「system.new.dat」 2.sdat2img:格式转换工具,用于将「system.new.dat」文件转换为ext4格式的「system.new.img...
AndroidROM刷机脚本updater-script的基本流程和初级语句说明[整理].pdf
This version of the System ROM contains updates aligned with the Intel Product Update (IPU) version IPU.2023.1 guidance. Deliverable Name: HPE ProLiant DL380/DL360 Gen9 System ROM - P89 Release ...
可用附件中的simg2img.exe来转化一下原始的system.img,然后再用其中的ext2Explorer来浏览提取system.img中的内容。 用法:1、将system.img改名为system.img.ext4。2、命令行cd到simg2img.exe目录下,执行命令“simg...
安卓系统ROM编辑工具 Android_ROM_Tool_v2.0.1
2012-09-20 00:18 524,288 ppc_rom.bin 2012-09-20 00:18 67,072 pxe-e1000.rom 2012-09-20 00:18 61,440 pxe-eepro100.rom 2012-09-20 00:18 61,440 pxe-ne2k_pci.rom 2012-09-20 00:18 61,440 pxe-pcnet.rom 2012-...
ext4_utils android rom 解包工具, 三星 i9300 rom转换 2020.2.15更新:删除下载积分要求,全部免分下载
This is an Arduion based NES controller for Android phones. It uses Amarino with a Bluesmirf for communication. Video at http://www.youtube.com/watch?v=_FZTz2KO9vU . I bought an NES contoller and ...
The First Practical, Hands-On Guide to Embedded System Programming for Android Today, embedded systems programming is a more valuable ...Create your own Android ROM on a virtual Android device
制作 Android ROM的步骤
HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解HD-ROM分解
Android-Kitchen-0.197-0(汉化版).zip 安卓厨房 制作rom的工具
就是对于使用者来说,并不知道他会把apk怎么样), 是模块化的基础。 ###DroidPlugin的缺点是什么? - a.通知栏限制(无法在插件中发送具有自定义资源的Notification,例如: 1. 带自定义RemoteLayout的...
安卓系统ROM编辑工具 Android_ROM_Tool_v2.0.3
The sections below describe the system and software requirements for developing Android applications using the Android SDK tools included in Android 1.1 SDK, Release 1. Supported Supported Supported ...