Android學(xué)習(xí)之Build環(huán)境初探
這里略過對android在手機(jī)上的文件系統(tǒng)框架的闡述(google或者baidu都能幫助你找到對應(yīng)的信息),主要看google是如何把生成合適的rootfs的工作整合到它的build體系當(dāng)中,同時,會順帶看一下CyanogenMod中對應(yīng)各種機(jī)型的build機(jī)制。
首先,來看一下Android的build系統(tǒng)中,使用到的編譯選項和相關(guān)工具
具體的目錄在:mydroid/build/tools/下
|-- acp
這是一個稍微改良的cp命令,用來應(yīng)付在windows/MAC/Linux下的cp命令的缺陷,其中的README很值得一看!
|-- adbs
這是一個用來查看crash問題的工具,詳細(xì)請看《Android調(diào)試工具之a(chǎn)dbs》
|-- Android.mk
|-- apicheck
用來進(jìn)行發(fā)布前的API檢查(參見mydroid/build/core/tasks/apicheck.mk),是否新編譯的系統(tǒng)中有破壞API兼容性或是非法的API
這里的代碼是用Java寫的用來檢查編譯時生成的API相關(guān)信息的xml文件(mydroid/framework/base/api/中),可以參考里面對于xml文件解析的代碼
|-- apriori
實現(xiàn)prelink的工具,簡單介紹參見(mydroid/bionic/linker/README.TXT)
|-- atree
為android SDK服務(wù)的一個工具,用來按照指定xxx.atree文件中的內(nèi)容進(jìn)行一些文件操作
|-- bin2asm
不太明白具體的用處,應(yīng)該是用來應(yīng)付mac上編譯android一些與gcc相關(guān)的問題
|-- buildinfo.sh
生成target中的各種xxx.prop文件,如system.prop, build.prop等
|-- check_builds.sh
包裝了diff,用來看2個發(fā)布版本之間變化
|-- check_prereq
device上進(jìn)行ota升級時的工具之一
|-- compare_fileslist.py
與check_builds.sh配合完成版本比較的腳本
|-- droiddoc
Android更具javadoc的一些移植
|-- dump-package-stats
簡單的查看一個jar/apk文件內(nèi)的dex和其它文件的大小信息
|-- event_log_tags.py
處理event-log-tags的內(nèi)容,關(guān)于event-log-tags文件的意義參見《Android學(xué)習(xí)之event-log-tags是神馬》
|-- fileslist.py
簡化的列出指定目錄下所有文件及大小的腳本 -- 可以放入自己的工具庫了使用:)
|-- findleaves.py
在指定目錄中(可多個)找指定文件的腳本 -- 可以放入自己的工具庫了使用:)
|-- fixlinebreaks.sh
把windows中的換行改為linux下的 -- 可以放入自己的工具庫了使用:)
|-- fs_config
列出指定文件夾及文件的權(quán)限
|-- fs_get_stats
得到指定文件夾下文件的簡單stats信息
|-- iself
判斷文件是否是ELF格式
|-- isprelinked
判斷文件是否是prelink過的
|-- java-event-log-tags.py
處理event-log-tags的內(nèi)容,關(guān)于event-log-tags文件的意義參見《Android學(xué)習(xí)之event-log-tags是神馬》
|-- kcm
key character map的工具, 相關(guān)資料參照:http://www.kandroid.org/online-pdk/guide/keymaps_keyboard_input.html#androidKeymapKeyCharMap
|-- lsd
!!!!!! ???
|-- merge-event-log-tags.py
處理event-log-tags的內(nèi)容,關(guān)于event-log-tags文件的意義參見《Android學(xué)習(xí)之event-log-tags是神馬》
|-- mktarball.sh
與fs_get_stats配合而執(zhí)行的打包工具
|-- print_module_licenses.sh
顯示當(dāng)前目錄下所有module信息
|-- releasetools
-- check_target_files_signatures
|-- common.py
|-- edify_generator.py
|-- img_from_target_files
|-- ota_from_target_files
`-- sign_target_files_apks
|-- rgb2565
rgb轉(zhuǎn)換工具
|-- signapk
命令行下對jar包簽名的工具
|-- soslim
Android定制的編譯工具之一,簡單介紹參見(mydroid/bionic/linker/README.TXT)
|-- warn.py
解析Android系統(tǒng)編譯log的工具
`-- zipalign
zipfile的對齊工具,參見該文件夾下的README.TXT
在來看看Android編譯系統(tǒng)中定義的一些通用XXX.mk文件
mydroid/build/core/
|-- armelflib.x
|-- armelf.x
|-- armelf.xsc
|-- base_rules.mk
|-- binary.mk
|-- build_id.mk
|-- build-system.html
|-- checktree
|-- cleanbuild.mk
|-- cleanspec.mk
|-- clear_vars.mk
|-- combo
|-- config.mk
|-- copy_headers.mk
|-- definitions.mk
|-- device.mk
|-- dex_preopt.mk
|-- distdir.mk
|-- droiddoc.mk
|-- dumpvar.mk
|-- dynamic_binary.mk
|-- envsetup.mk
|-- executable.mk
|-- filter_symbols.sh
|-- find-jdk-tools-jar.sh
|-- help.mk
|-- host_executable.mk
|-- host_java_library.mk
|-- host_native_test.mk
|-- host_prebuilt.mk
|-- host_shared_library.mk
|-- host_static_library.mk
|-- java_library.mk
|-- java.mk
|-- legacy_prebuilts.mk
|-- main.mk
|-- Makefile
|-- multi_prebuilt.mk
|-- native_test.mk
|-- node_fns.mk
|-- notice_files.mk
|-- package.mk
|-- pathmap.mk
|-- phony_package.mk
|-- prebuilt.mk
|-- process_wrapper_gdb.cmds
|-- process_wrapper_gdb.sh
|-- process_wrapper.sh
|-- product_config.mk
|-- product.mk
|-- proguard.flags
|-- proguard_tests.flags
|-- raw_executable.mk
|-- raw_static_library.mk
|-- root.mk[!--empirenews.page--]
|-- shared_library.mk
|-- static_java_library.mk
|-- static_library.mk
|-- tasks
|-- user_tags.mk
`-- version_defaults.mk
這里,目錄在mydroid/build/core/tasks/有一些特別的task
|-- apicheck.mk, 判斷api是否符合AOSP的規(guī)范
|-- cts.mk cts測試, 可以在代碼根目錄, make cts, 編譯結(jié)束之后,進(jìn)入out/host/linux-x86/bin/下,執(zhí)行cts命令
|-- ide.mk IDE開發(fā)環(huán)境
|-- product-graph.mk
`-- sdk-addon.mk
NDK的build環(huán)境沒有包含在標(biāo)注難得AOSP的/build/目錄下
而是在mydroid/ndk/build下
$ cd ndk/build/tools
$ export ANDROID_NDK_ROOT=aosp-root/ndk
$ ./make-release --help
一些小技巧
如何顯示每次編譯所包含的所有xxx.mk文件
找到build/core/main.mk
把include $(subdir_makefiles)替換為
[plain] view plaincopy $(foreach subdir_makefile, $(subdir_makefiles), \
$(info Including $(subdir_makefile)) \
$(eval include $(subdir_makefile)) \
)
subdir_makefile :=
如果遇見API相關(guān)的PACKAGING/checkapi-current-timestamp] Error 38
需要執(zhí)行:make update-api
如何在AOSP代碼目錄之外編譯
[plain] view plaincopy # Paths and settings
TARGET_PRODUCT = generic
ANDROID_ROOT = /home/karim/android/aosp-2.3.x
BIONIC_LIBC = $(ANDROID_ROOT)/bionic/libc
PRODUCT_OUT = $(ANDROID_ROOT)/out/target/product/$(TARGET_PRODUCT)
CROSS_COMPILE = \
$(ANDROID_ROOT)/prebuilt/linux-x86/toolchain/arm-eabi-4.4.3/bin/arm-eabi-
# Tool names
AS = $(CROSS_COMPILE)as
AR = $(CROSS_COMPILE)ar
CC = $(CROSS_COMPILE)gcc
CPP = $(CC) -E
LD = $(CROSS_COMPILE)ld
NM = $(CROSS_COMPILE)nm
OBJCOPY = $(CROSS_COMPILE)objcopy
OBJDUMP = $(CROSS_COMPILE)objdump
RANLIB = $(CROSS_COMPILE)ranlib
READELF = $(CROSS_COMPILE)readelf
SIZE = $(CROSS_COMPILE)size
STRINGS = $(CROSS_COMPILE)strings
STRIP = $(CROSS_COMPILE)strip
export AS AR CC CPP LD NM OBJCOPY OBJDUMP RANLIB READELF \
SIZE STRINGS STRIP
# Build settings
CFLAGS = -O2 -Wall -fno-short-enums
HEADER_OPS = -I$(BIONIC_LIBC)/arch-arm/include \
-I$(BIONIC_LIBC)/kernel/common \
-I$(BIONIC_LIBC)/kernel/arch-arm
LDFLAGS = -nostdlib -Wl,-dynamic-linker,/system/bin/linker \
$(PRODUCT_OUT)/obj/lib/crtbegin_dynamic.o \
$(PRODUCT_OUT)/obj/lib/crtend_android.o \
-L$(PRODUCT_OUT)/obj/lib -lc -ldl
# Installation variables
EXEC_NAME = example-app
INSTALL = install
INSTALL_DIR = $(PRODUCT_OUT)/system/bin
# Files needed for the build
OBJS = example-app.o
# Make rules
all: example-app
.c.o:
$(CC) $(CFLAGS) $(HEADER_OPS) -c {1}lt;
example-app: ${OBJS}
$(CC) -o $(EXEC_NAME) ${OBJS} $(LDFLAGS)
install: example-app
test -d $(INSTALL_DIR) || $(INSTALL) -d -m 755 $(INSTALL_DIR)
$(INSTALL) -m 755 $(EXEC_NAME) $(INSTALL_DIR)
clean:
rm -f *.o $(EXEC_NAME) core
distclean:
rm -f *~
rm -f *.o $(EXEC_NAME) core
如何增加一個新的設(shè)備
[plain] view plaincopy $ cd ~/android/aosp-2.3.x
$ . build/envsetup.sh
$ mkdir -p device/acme/coyotepad
$ cd device/acme/coyotepad
進(jìn)入AndroidProducts.mk
PRODUCT_MAKEFILES := \
$(LOCAL_DIR)/full_coyotepad.mk
對于full_coyotepad.mk
$(call inherit-product, $(SRC_TARGET_DIR)/product/languages_full.mk)
$(call inherit-product, $(SRC_TARGET_DIR)/product/full.mk)
DEVICE_PACKAGE_OVERLAYS :=
PRODUCT_PACKAGES +=
PRODUCT_COPY_FILES +=
PRODUCT_NAME := full_coyotepad
PRODUCT_DEVICE := coyotepad
PRODUCT_MODEL := Full Android on CoyotePad, meep-meep
在BoardConfig.mk中
TARGET_NO_KERNEL := true
TARGET_NO_BOOTLOADER := true
TARGET_CPU_ABI := armeabi
BOARD_USES_GENERIC_AUDIO := true
USE_CAMERA_STUB := true
打開vendorsetup.sh
add_lunch_combo full_coyotepad-eng