aosp_002.ubuntu18.04搭建编译环境

本文详细介绍了在Python2环境下搭建AOSP源码编译环境的步骤,包括安装openjdk8、配置java版本、安装依赖包、使用repo管理源码、编译环境初始化、编译目标设置、编译过程及常见错误解决方法。同时,还提供了模块编译、SDK编译、framework编译的具体命令,以及如何将编译后的模块集成到系统镜像中。

搭建编译环境:

在python2环境进行操作

1、安装openjdk8

sudo apt-get install openjdk-8-jdk
sudo apt-get install openjdk-8-jre

配置java版本

sudo update-alternatives --config java
sudo update-alternatives --config javac

2、安装依赖包

sudo apt install git-core gnupg flex bison gperf build-essential zip curl zlib1g-dev gcc-multilib g++-multilib libc6-dev-i386 lib32ncurses5-dev x11proto-core-dev libx11-dev lib32z-dev libgl1-mesa-dev libxml2-utils xsltproc unzip ccache

下载源码:

AOSP的代码管理是基于git的管理方式,但是是由几百个git仓库构成的,这几百个git仓库统一管理就必要要有一个统一的工具,google的工程师用python写了个脚本叫repo,使用它来进行管理android的中每个git仓库对应的版本。

安装git和repo并配置

sudo apt-get install git repo
git config --global user.name "your name"
git config --global user.email "XXX@XXX.com"

配置repo

vim ~/.bashrc
export REPO_URL='https://mirrors.tuna.tsinghua.edu.cn/git/git-repo/'

配置其它

vim ~/.bashrc
#添加以下内容
export USE_CCACHE=1
export CCACHE_COMPRESS=1
export LC_ALL=C

下载源码

mkdir aosp
cd aosp
repo init -u https://aosp.tuna.tsinghua.edu.cn/platform/manifest
#或者下载特定分支
repo init -u https://aosp.tuna.tsinghua.edu.cn/platform/manifest -b android-4.0.1_r1
#分支网址:https://source.android.com/setup/start/build-numbers.html
repo sync #开始下载

推荐使用清华大学镜像:
将 https://android.googlesource.com/ 全部使用 https://aosp.tuna.tsinghua.edu.cn/代替

开始编译:

cd aosp
. build/envsetup.sh #初始化编译环境
lunch #设置编译目标
make #开始编译 可选参数 -j  指定编辑线程数目
emulator #编译成功后,运行模拟器

 

 

 

 

 

#使用emulator时,虚拟机停在黑屏界面,点击无任何响应.此时,可能是kerner内核问题,解决方法如下:
#执行如下命令:
./out/host/linux-x86/bin/emulator -partition-size 1024 -kernel ./prebuilts/qemu-kernel/arm/kernel-qemu-armv7 

#使用emulator出现comand not found,需要编译sdk
source ./build/envsetup.sh
lunch sdk
#或者
make sdk

#出现
#emulator: ERROR: x86_64 emulation currently requires hardware acceleration!
#Please ensure KVM is properly installed and usable.
#CPU acceleration status: This user doesn't have permissions to use KVM (/dev/kvm)

sudo apt-get install qemu-kvm cpu-checker
sudo addgroup kvm
sudo usermod -a -G kvm 你的用户名
sudo chgrp kvm /dev/kvm
sudo vim /etc/udev/rules.d/60-qemu-kvm.rules
#添加
KERNEL=="kvm", GROUP="kvm", MODE="0660"




#通过使用kernel-qemu-armv7内核 解决模拟器等待黑屏问题.而-partition-size 1024 则是解决警告: #system partion siez adjusted to match image file (163 MB >66 MB)
#如果你一开始编译的版本是aosp_arm-eng,使用上述命令仍然不能解决等待黑屏问题时,不妨编译#aosp_arm64-eng试试.

 

编译成功后,我们使用vendorsetup.sh脚本里面的pack函数将编译出来的镜像文件打包成rom,红色部分表示生成的路径。


出现错误:

mkfs.fat: warning - lowercase labels might not work properly with DOS or Windows
mkfs.fat 4.1 (2017-01-24)
.....
AssertionError: Can only handle FAT with 1 reserved sector
.....
ninja: build stopped: subcommand failed.
14:59:40 ninja failed with: exit status 1

解决方法:暂无

 

出现错误:

subcommand failed.
20:38:09 ninja failed with: exit status 1
build/core/main.mk:24: recipe for target 'run_soong_ui' failed
make: *** [run_soong_ui] Error 1

#### make failed to build some targets (28:58 (mm:ss)) ####

解决方法:

sudo apt-get install aptitude 
sudo aptitude install libx11-dev:i386 libreadline6-dev:i386 libgl1-mesa-dev g++-multilib 
sudo aptitude install -y git flex bison gperf build-essential libncurses5-dev:i386
sudo aptitude install tofrodos python-markdown libxml2-utils xsltproc zlib1g-dev:i386 
sudo aptitude install dpkg-dev libsdl1.2-dev libesd0-dev
sudo aptitude install git-core gnupg flex bison gperf build-essential
sudo aptitude install zip curl zlib1g-dev gcc-multilib g++-multilib
sudo aptitude install libc6-dev-i386
sudo aptitude install lib32ncurses5-dev x11proto-core-dev libx11-dev
sudo aptitude install libgl1-mesa-dev libxml2-utils xsltproc unzip m4
sudo aptitude install lib32z-dev ccache

 


关于编译介绍

  1. 在aosp根目录下, out目录是编译之后产生的, 具体介绍如下:
  • out/target/product/[generic]/system: 其中, []表示的目录是根据你lunch选项生成的, 例如generic_arm64表示生成的是arm架构的64问系统.
  • out/target/product/generic/system/apk: Android系统自带的apk文件
  • out/target/product/generic/system/bin: 一些可执行文件(比如C编译的执行)
  • out/target/product/generic/system/lib: 动态链接库;
  • out/targer/product/generic/system/lib/hw: 硬件抽象层文件

模块编译

https://bbs.youkuaiyun.com/topics/370150557

除了通过make命令编译可以整个android源码外,Google也为我们提供了相应的命令来支持单独模块的编译.

编译环境初始化(即执行source build/envsetup.sh)之后,我们可以得到一些有用的指令,除了上边用到的lunch,还有以下:

 Invoke ". build/envsetup.sh" from your shell to add the following functions to your environment:
 - lunch:     lunch <product_name>-<build_variant>
              Selects <product_name> as the product to build, and <build_variant> as the variant to
              build, and stores those selections in the environment to be read by subsequent
              invocations of 'm' etc.
 - tapas:     tapas [<App1> <App2> ...] [arm|x86|mips|arm64|x86_64|mips64] [eng|userdebug|user]
 - croot:     Changes directory to the top of the tree.
 - m:         Makes from the top of the tree.
 - mm:        Builds all of the modules in the current directory, but not their dependencies.
 - mmm:       Builds all of the modules in the supplied directories, but not their dependencies.
              To limit the modules being built use the syntax: mmm dir/:target1,target2.
 - mma:       Builds all of the modules in the current directory, and their dependencies.
 - mmma:      Builds all of the modules in the supplied directories, and their dependencies.
 - provision: Flash device with all required partitions. Options will be passed on to fastboot.
 - cgrep:     Greps on all local C/C++ files.
 - ggrep:     Greps on all local Gradle files.
 - jgrep:     Greps on all local Java files.
 - resgrep:   Greps on all local res/*.xml files.
 - mangrep:   Greps on all local AndroidManifest.xml files.
 - mgrep:     Greps on all local Makefiles files.
 - sepgrep:   Greps on all local sepolicy files.
 - sgrep:     Greps on all local source files.
 - godir:     Go to the directory containing a file.

其中mmm指令就是用来编译指定目录.通常来说,每个目录只包含一个模块.比如这里我们要编译Launcher2模块,执行指令:

mmm packages/apps/Launcher2/

稍等一会之后,如果提示:
### make completed success fully ###
即表示编译完成,此时在out/target/product/gereric/system/app就可以看到编译的Launcher2.apk文件了.

重新打包系统镜像
编译好指定模块后,如果我们想要将该模块对应的apk集成到系统镜像中,需要借助make snod指令重新打包系统镜像,这样我们新生成的system.img中就包含了刚才编译的Launcher2模块了.重启模拟器之后生效.

单独安装模块
我们在不断的修改某些模块,总不能每次编译完成后都要重新打包system.img,然后重启手机吧?有没有什么简单的方法呢?
在编译完后,借助adb install命令直接将生成的apk文件安装到设备上即可,相比使用make snod,会节省很多事件.

2.编译命令及解释

编译指令    解释
m    在源码树的根目录执行编译
mm    编译当前路径下所有模块,但不包含依赖
mmm [module_path]    编译指定路径下所有模块,但不包含依赖
mma    编译当前路径下所有模块,且包含依赖
mmma [module_path]    编译指定路径下所有模块,且包含依赖
make [module_name]    无参数,则表示编译整个Android代码


下面列举部分模块的编译指令:

模块    make命令    mmm命令
init    make init    mmm system/core/init
zygote    make app_process    mmm frameworks/base/cmds/app_process
system_server    make services    mmm frameworks/base/services
java framework    make framework    mmm frameworks/base
framework资源    make framework-res    mmm frameworks/base/core/res
jni framework    make libandroid_runtime    mmm frameworks/base/core/jni
binder    make libbinder    mmm frameworks/native/libs/binder

 

补充
我们简单的来介绍out/target/product/generic/system目录下的常用目录:
Android系统自带的apk文件都在out/target/product/generic/system/apk目录下;
一些可执行文件(比如C编译的执行),放在out/target/product/generic/system/bin目录下;
动态链接库放在out/target/product/generic/system/lib目录下;
硬件抽象层文件都放在out/targer/product/generic/system/lib/hw目录下.

 


SDK编译

如果你需要自己编译SDK使用,很简单,只需要执行命令make sdk即可.

 


 

编译framework

 

# 先在framework/base目录下执行
mmm core/res/      # 生成framework-res.apk
# 然后再返回aosp目录,单独编译framework
mmm frameworks/base

编译好模块后,还要重新打包一下system.img文件(重打包命令如下),这样我们把system.img运行在模拟器上时,就可以看到我们的程序了。

make snod

将源码导入android studio

#编译idegen这个项目,生成idegen.jar文件。
mmm development/tools/idegen/
#生成:android.iws, android.ipr, android.iml这个三个文件。
sudo ./development/tools/idegen/idegen.sh
#android.iws 包含工作区的个人设置,比如打开过的文件,版本控制工具的配置,本地修改历史,运行和#debug的配置等。
#android.ipr 一般保存了工程相关的设置,比如modules和modules libraries的路径,编译器配置,入口#点等。
#android.iml 用来描述modules。它包括modules路径、 依赖关系,顺序设置等。一个项目可以包含多个 #*.iml 文件。

打开Android Studio --> File --> open --> 选中生成的android.ipr文件,确定后就会导入整个源码。

 

为了加快读取速度,我们定义一些不需要读取的文件夹,比如 build、.repo、device、out 等等。

vim android.iml
#
发现大标签只有三种
<sourceFolder />
<excludeFolder />
<orderEntry />

关于<sourceFolder>标签:
去除不需要debug的<sourceFolder/>标签内容,通常我们只需要frameworks和packages两个目录,所以保留这两个目录有关的标签就行,其他全部删掉,这样索引的速度就会加快了。
关于<excludeFolder>标签:
exclude顾名思义就是不包含的意思。我们有很多目录直接就不想让Studio去管它,不管是索引还是什么等等,所以只需要将这些目录配置到<excludeFolder>中就好了。

** 我这里只保留了framworks和packages模块,将其他模块全部排除了,因此在android.iml中添加了以下配置: 剩下的都删了**

#
<?xml version="1.0" encoding="UTF-8"?>
<module version="4" relativePaths="true" type="JAVA_MODULE">
  <component name="ModuleRootManager" />
  <component name="NewModuleRootManager" inherit-compiler-output="true">
    <exclude-output />
    <content url="file://$MODULE_DIR$">
      <!--sourceFolder标签表示需要索引的代码目录-->
      <sourceFolder url="file://$MODULE_DIR$/frameworks/base/core/java" isTestSource="false" />
      <sourceFolder url="file://$MODULE_DIR$/gen" isTestSource="false" generated="true" />
      <!--excludeFolder标签表示这个目录下所有内容都不索引-->
      <excludeFolder url="file://$MODULE_DIR$/.repo" />
      <excludeFolder url="file://$MODULE_DIR$/abi" />
      <excludeFolder url="file://$MODULE_DIR$/art" />
      <excludeFolder url="file://$MODULE_DIR$/bionic" />
      <excludeFolder url="file://$MODULE_DIR$/bootable" />
      <excludeFolder url="file://$MODULE_DIR$/build" />
      <excludeFolder url="file://$MODULE_DIR$/cts" />
      <excludeFolder url="file://$MODULE_DIR$/dalvik" />
      <excludeFolder url="file://$MODULE_DIR$/developers" />
      <excludeFolder url="file://$MODULE_DIR$/development" />
      <excludeFolder url="file://$MODULE_DIR$/device" />
      <excludeFolder url="file://$MODULE_DIR$/docs" />
      <excludeFolder url="file://$MODULE_DIR$/external" />
      <excludeFolder url="file://$MODULE_DIR$/external/bluetooth" />
      <excludeFolder url="file://$MODULE_DIR$/external/chromium" />
      <excludeFolder url="file://$MODULE_DIR$/external/emma" />
      <excludeFolder url="file://$MODULE_DIR$/external/icu4c" />
      <excludeFolder url="file://$MODULE_DIR$/external/jdiff" />
      <excludeFolder url="file://$MODULE_DIR$/external/webkit" />
      <excludeFolder url="file://$MODULE_DIR$/frameworks/base/docs" />
      <excludeFolder url="file://$MODULE_DIR$/frameworks/base/tests" />
      <excludeFolder url="file://$MODULE_DIR$/frameworks/base/tools" />
      <excludeFolder url="file://$MODULE_DIR$/hardware" />
      <excludeFolder url="file://$MODULE_DIR$/libcore" />
      <excludeFolder url="file://$MODULE_DIR$/libnativehelper" />
      <excludeFolder url="file://$MODULE_DIR$/ndk" />
      <excludeFolder url="file://$MODULE_DIR$/out" />
      <excludeFolder url="file://$MODULE_DIR$/pdk" />
      <excludeFolder url="file://$MODULE_DIR$/platform_testing" />
      <excludeFolder url="file://$MODULE_DIR$/prebuilt" />
      <excludeFolder url="file://$MODULE_DIR$/sdk" />
      <excludeFolder url="file://$MODULE_DIR$/tools" />
      <excludeFolder url="file://$MODULE_DIR$/vendor" />
      <excludeFolder url="file://$MODULE_DIR$/toolchain" />
      <excludeFolder url="file://$MODULE_DIR$/system" />
      <excludeFolder url="file://$MODULE_DIR$/prebuilts" />
    </content>

    <orderEntry type="sourceFolder" forTests="false" />
    <orderEntry type="inheritedJdk" />
    <orderEntryProperties />
  </component>
</module>

接下来,修改JDK + SDK,适配编译使用的jdk和sdk版本

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值