BoardConfig.mk(device文件夹里):该文件用来配置硬件主板,它其中定义的都是设备底层的硬件特性。例如:该设备的主板相关信息,Wifi 相关信息,还有 bootloader,内核,radioimage 等信息。对于该文件的示例,请参看 Android 源码树已经有的文件。html
vendorsetup.sh:该文件中做用是经过 add_lunch_combo 函数在 lunch 函数中添加一个菜单选项。该函数的参数是产品名称加上编译类型,中间以“-”链接,例如:add_lunch_combo full_lt26-userdebug。/build/envsetup.sh 会扫描全部 device 和 vender 二 级目 录下的名称 为"vendorsetup.sh"文件,并根据其中的内容来肯定 lunch 函数的 菜单选项。java
使用“include FILENAMES...”,make程序处理时,若是“FILENAMES”列表中的任何一个文件不能正常读取并且不存在一个建立此文件的规则时make程序将会提示错误并退出。linux
使用“-include FILENAMES...”的状况是,当所包含的文件不存在或者不存在一个规则去建立它,make程序会继续执行,只有真正因为不能正确完成终极目标的重建时(某些必需的目标没法在当前已读取的makefile文件内容中找到正确的重建规则),才会提示致命错误并退出。android
Make[flag][macro_definition][targets]c++
Makefile文件中:sql
.PHONY: cts //target:cts 一个target会定义一些规则shell
$ . build/envsetup.sh //配置选项,并编译android源码
$ make cts //android源码编译好后,在编译cts数据库
build\core\version_defaults.mk //搜索该文件中的 PLATFORM_VERSION值
m:编译全部的模块
mm:编译当前目录下的模块,当前目录下要有Android.mk文件
mmm [dir]:编译指定路径下的模块,指定路径下要有Android.mk文件 api
Makesnod:修改了out/target中的内容,在源码根目录使用后,能够生成新的img安全
单独编译模块:
1> source build/envsetup.sh:加载命令
2> lunch:选择平台编译选项(选择本身产品自定义的编译选项)
3> make:执行编译
Make clean/make distclean
0)Kernel编译使用JLB带的编译器, Android自成Boot.img, recovery.img须要zImage. 因此上面Clone下来的代码须要放在同一目录下
1)uboot
#> cd UBOOT_DIR
#> vi Makefile //修改CROSS COMPILE路径, 默认为/usr/local/arm/arm-2009q3/bin/arm-none-linux-gnueabi-, 相符可跳过
#> make tg4_dvt_config
#> make -j4
2)Kernel
#> cd KERNEL_DIR
#> ./build_kernel.sh tg4_dvt wqxga
3)Android
#> cd ANDROIR_DIR
#> ./build.sh tg4_dvt
编译sc1 kernel:
1.make sc1_dvt1_defconfig
2.make
make snod //把system文件夹打包为system.img
注:经过mmm packages/providers/ContactsProvider/ 编译后的apk在 out/target/product/generic/system/app
make 2&>txt
将make的信息输出到txt中,若是make > txt则没法输入
Linux Shell 环境中支持输入输出重定向,用符号"<"和">"来表示。0、1和2分别表示标准输入、标准输出和标准错误信息输出,能够用来指定须要重定向的标准输入或输出
make &>test
表示标准和错误所有输出
Java Build Path是咱们编译时所须要的包,在咱们import某个包的时候,若是没有Java Build Path导入包的话,类里面就会有红叉,不可以识别这个类,复制到libs下是运行时所须要的包。若是用Add Buid Path导入包,可是没有放在libs下程序也会报ClassNotFindException
include $(BUILD_EXECUTABLE)表示要编译成一个可执行文件(其实就是加载了$(BUILD_SYSTEM)/executable.mk),若是想编译成动态库则可用BUILD_SHARED_LIBRARY,这些能够在$(YOUR_ANDROID)/build/core/config.mk查到。
LOCAL_PRIVILEGED_MODULE := true,以声明app须要放在/system/priv-app下
LOCAL_MODULE:打出的库名 or 指定为用于注册库的 .xml 文件
LOCAL_AAPT_FLAGS: 引用其余模块的资源,将几个模块打成一个app
LOCAL_PACKAGE_NAME:package的名字,这个名字在脚本中将标识这个app或package
LOCAL_JAVA_LIBRARIES:当前模块依赖的 Java 共享库。
LOCAL_STATIC_JAVA_LIBRARIES:当前模块依赖的 Java 静态库。
LOCAL_STATIC_LIBRARIES: 表示该模块须要使用哪些静态库,以便在编译时进行连接。
LOCAL_SHARED_LIBRARIES: 表示模块在运行时要依赖的共享库(动态库),在连接时就须要,以便在生成文件时嵌入其相应的信息。
A. 静态库的名字通常是libxxx.a;利用静态函数库编译成的文件比较大,由于整个函数库的全部数据都被整合进目标代码中Android。建立命令:ar –cr。Makefile使用“include $(BUILD_STATIC_JAVA_LIBRARY)”指定建立为静态库
B.动态库又称共享库,这类库的名字通常是libxxx.so;相对于静态函数库,动态函数库在编译的时候并无被编译进目标代码中,你的程序执行到相关函数时才调用函数库里的相应函数。建立命令:gcc –share。Makefile使用“include $(BUILD_JAVA_LIBRARY)”指定编译为动态库。
C. 注册第三方jar包。include $(BUILD_JAVA_LIBRARY) + include $(BUILD_PREBUILT)指定配置库的xml(LOCAL_MODULE := com.qrd.plugin.feature_query.xml)
.jar 文件:/system/framework/ (framework中模块的jar包打到这,第三方jar要xml中配置到这)
.xml 文件:/system/etc/permissions/
LOCAL_PREBUILT_STATIC_JAVA_LIBRARIES/LOCAL_PREBUILT_JAVA_LIBRARIES:利用外部jar包须要prebuilt
Avl7580 aricentimsclientsdk: LOCAL_MODULE_SUFFIX := .jar LOCAL_MODULE_CLASS := JAVA_LIBRARIES
LOCAL_MODULE := aricentimsclientsdk
LOCAL_SRC_FILES := aricentimsclientsdk.jar
#TARGET_OUT_JAVA_STATIC_LIBRARIES := out/target/common/obj/JAVA_LIBRARIES/aricentimsclientsdk_intermediates #LOCAL_PROGUARD_FLAG_FILES := proguard.flags
include $(BUILD_PREBUILT) |
$(call inherit-product-if-exists, device/.../xxx.mk)#指把xxx.mk(xxx.mk要存在)中的变量添加进来
修改google开放出来的类再进行编译,可能出现下面报错:
You have tried to change the API from what has been previously approved.
由于对javadoc的生成会产生影响。处理方法:
1, 添加 /**{@hide}*/ 修饰. 能够直接对整个类进行修饰。
2, 就是想要生成的javadoc里出现这个方法或变量,输入: make update-api,即编译时,输入make update-api PRODUCT-***-eng,可是输入 make PRODUCT-***-eng update-api 这样是有问题的,由于后面的update-api会被忽略掉,这样系统就会自动的把咱们新增的API 写入 frameworks/base/api/current.xml 文件中。或者手动更新更新 frameworks/base/api/current.txt 文件。(或者须要先手动修改current.txt再make update-api)
3, Android.mk LOCAL_SDK_VERSION := current 加了这个就不能调用了,没加能够调用
类或API是否开放,是经过doc的注释{@hide}来控制的。非开放类,便是在android应用程序中没法直接访问的类。
LOCAL_AIDL_INCLUDES: 在aidl接口的函数中使用本身定义的类作参数,只需将该类实现Parcelable接口,而且将该类存放的路径加入到LOCAL_AIDL_INCLUDES中,同时在该类的同一目录下建立aidl文件,就能够编译了。
amoled屏: make avl8890_eng_defconfig make menuconfig platform selection -》 samsung Exynos -》hardware platform selection -》component selection 选 Support Video LCD S6E8FA0, unselect(*去掉) Support Video LCD Truely NT35596 tp选 Support Touch Screen ATMELMXTS, unselect(*去掉)Support Touch Screen SYNAPTICSRMI4 保存退出 make
前缀必须用system\core\init\property_service.c中定义的前缀 ,进行系统属性设置的程序也必须有system或root权限
若是咱们要添加一个property:例如:silvan_liu
路径:system/core/rootdir/int.rc
在on post-fs-data 目录下
setprop persist.sys.silvan_liu 1//persist.sys 前缀名; 1为初始值
前缀必须用system\core\init\property_service.c中定义的前缀这和int.rc的语法有关。
若是属性名称以“ro.”开头,那么这个属性被视为只读属性。一旦设置,属性值不能改变。
若是属性名称以“persist.”开头,当设置这个属性时,其值也将写入/data/property。
c++中对应JAVA的两个函数就是property_set, property_get, JAVA是经过JNI调用这两个函数实现属性的设置和读取。
在adb shell能够经过如下的命名读取和修改:
#getprop persist.sys.language
#setprop persist.sys.language zh
在sc1项目中,自定义的属性文件:
android4.2.2_JLB_SC1\device\sc1_dvt1\ system.prop
android4.3_JLB_SC1\device\sscr\sc1_dvt1\ system.prop
咱们能够在下面文件中定义属性:
\device\sscr\sc1_dvt1\system.prop
例如:
ro.wifi.support.cmcc=true
这样,就能够在代码中经过“SystemProperties.get(“ro.wifi.support.cmcc”)”方法获取定义好的属性了。import android.os.SystemProperties;
最终,这些配置项会编译到image的/system/build.prop中。
系统的设置存于/data/data/PACKAGE_NAME/shared_prefs中(SharedPreferences)。
1, device\sc1_dvt1\BoardConfig.mk
HAVE_WLAN_CMCC_FEATURE := true
2,wpa_supplicant_8\wpa_supplicant\Android.mk
ifeq ($(HAVE_WLAN_CMCC_FEATURE),true) //能够识别别的mk定义的属性
L_CFLAGS += -DWLAN_CMCC_FEATURE
Endif
编译时引入其余包:
LOCAL_PREBUILT_STATIC_JAVA_LIBRARIES := simplexml:libs/simple-xml-2.3.4.jar
LOCAL_STATIC_JAVA_LIBRARIES := \
simplexml \
继承SQLiteOpenHelper,在OnCreate中建表,在onUpgrade中升级表。经过该类的getWritableDatabase和getReadableDatabase()能够得到 SQLiteDatabase的对象,从而增删改查表。
基于 android 系统的设备通常将存储区间逻辑上分为:引导区、内核区、 ramdisk 区间、 recovery 区、系统区、 cache 区间和数据区。
其中 reocvery 区间为系统修复时候使用,其余区间功能以下:引导区为处理器上电固定的加载点,其存储位置依据处理器不一样而变化,对于支持从 nand 加载引导固件的处理器,能够将引导区域直接放置到nandflash 中,通常占据从 nand 的 block0 开始的一些区域。不然必放置处处理器支持的加载点如 norflash 等。
Boot 代码负责操做系统的加载和升级,因为 boot 才能从一些基本的数据源如串口、 usb 获取升级数据,做为处理器上电即加载和运行的这一区域一旦损坏则系统升级只能凭借处理器内建原生的引导能力,这个过程大都须要专用工具或软件才能完成。
内核区即 linux 内核保存位置,其和引导区在最终系统中对通常用户都设计为不能进行升级以维护基本系统的安全性。
Ramdisk 和 recovery 区间同标准 linux 中的 initrd ,引导程序根据启动参数决定加载正常的 ramdisk 仍是 recovery 做为 initrd 传递给内核,其中 recovery 区间为修复系统使用,因为其为修复 / 升级系统的核心组件,通常也都设计为对用户不可改变。
系统区为正常的 android 应用保存位置,通常设计为对普通用户属只读系统以保护主要系统的安全性,数据区为用户设置信息、优化后的 DEX 和系统数据库保存位置,清空该区域会清除用户的全部数据以及优化过的 DEX 文件,致使下一次启动过程很长(须要从新建立 data 目录中的缺省信息)。
Cache 区间为升级过程使用的临时存储区。
升级过程主要流程描述以下:
1 boot 发现用户按住升级按键,将 recovery.img 做为 ramdisk 读取到内存。
2 内核根据 ramdisk 中的 init.rc 执行 recovery 脚本。 Recovery 脚本在 sdcard 中找到升级文件后调用 recovery 程序依次作如下操做:
A 检查升级文件的数字签名是否可靠。检查签名使用的本地密钥为 /res/keys
B 若是签名合法则执行提取压缩包中 META-INF/com/google/android/update-binary 文件重命名到 /tmp/update_binary 并执行该文件。
C update_binary 解析压缩文件中的 META-INF/com/google/android/updater-script 文件并执行。其升级进度经过管道回传给 recovery 程序。升级 / 更新能够直接覆盖目标文件,也可采用二进制补丁形式以减小升级文件的容量,采用的工具为 bsdiff 和 imgdiff 。对于补丁包升级形式,升级数据源可靠性鉴别的依据为 sha1 校验和数据长度比对。具体要求为: 1 升 级包提供的目标文件的 sha1 值和目标文件计算值符合,即目标正确。 2 进行补丁后的文件 sha1 值和长度符合升级包提供的补丁后的目标文件的长度和 sha1 数值,保证结果正确。两项有一项不符合则升级过程中止。为保证第二项操做不损毁最终目标,打补丁的文件会先临时存储到 cache 中,等到结果比对正确才进行实际写入 / 替换目标文件操做。因此此过程要求 cache 目录必须有足够空间可以保存临时文件。
DEVICE_PACKAGE_OVERLAYS能够设定路径,起到的做用就是替换掉原来的目录中的资源,好比图片等等,唯一的要求就是必须创建和原来图片位置相同的路径
有两种不一样的overaly目录定义,来影响最终的效果:
PRODUCT_PACKAGE_OVERLAYS: used by a particular product
DEVICE_PACKAGE_OVERLAYS: used several products that share a common device model
若是包含同一资源,那么 PRODUCT_PACKAGE_OVERLAYS 将覆盖 DEVICE_PACKAGE_OVERLAYS
中的
例:device\samsung\avl7580\device.mk
DEVICE_PACKAGE_OVERLAYS := \
device/samsung/avl7580/overlay
init.c 、init.rc init.xx.rc 等最终会编译到ramdisk.img(根文件系统)中,和kernel一块儿打包成boot.img。android启动后每次都会从boot.img中解压出init.c等文件到内存
在init.rc中启动的服务,都是以一个进程的形式运行,属于android的本地服务。经过在终端输入PS命令能够查看在运行的相应进程,他们的ppid都为1,表明init进程。 init进程也是android系统启动的第一个应用进程
首先在boardconfig.mk里定义SELinux的poliocy文件:
BOARD_SEPOLICY_DIRS += \
vendor/samsung_slsi/telephony/common/config/sepolicy
而后在pliocy文件中写权限:
allow system_server radio_service:service_manager add;