Android9.0系统源码_编译刷机——从下载到编译

前言

近期因工作原因,需要频繁编译、调试Android源码 ,特别是修改framework层的源码,经过不懈努力,终于可以正常调试了。
这里进行一些总结和分享。
参考文章:清华镜像之Android 镜像使用帮助、Android系统源码编译

一、环境准备

1、ubuntu24.04(250G+6核+16GRAM)
2、VirtualBox6.1.34

至于VirtualBox如何安装ubuntu24.04,请参考我的另一篇文章:使用VirtualBox安装Ubuntu系统

二、安装repo

1、简介
Repo 是我们以 Git 为基础构建的代码库管理工具。Repo 可以在必要时整合多个 Git 代码库,将相关内容上传到我们的修订版本控制系统,并自动执行 Android 开发工作流程的部分环节。Repo 并非用来取代 Git,只是为了让您在 Android 环境中更轻松地使用 Git,Repo的常见应用场景:

  • 大型软件开发项目:多仓,多分支,多流程
  • 多仓管理:多责任田,多评审网站等
  • 搭配Gerrit使用

由于Android系统源码是非常庞大的,而且每个模块都是用git来进行管理 ,整个Android源码是由很多个git项目构成,Google对Android代码的更新也是更新到相应模块的git项目上。那对于需要编译Android的开发者来说,要分别clone 每个git项目而且还要放到固定的位置确实是件惨绝人寰的事,所以Google就开发了一个基于Python编写的帮助开发者管理多个项目的工具,这个工具就叫repo,repo就是封装了git命令的python脚本。

2、 安装python3

由于Python 2 的支持已于 2020 年 1 月 1 日停止,现在的Repo也必须使用Python 3。

apt-get install python3
alias python=python3

3、安装Git & 配置Git信息

sudo apt-get install git
git config --global user.name "afinalstone"
git config --global user.email "[email protected]"
git config --list

4、安装curl

sudo apt-get install curl

5、 安装repo
由于国内网络的原因,这里我使用的是清华源来下载源码和repo工具,在下载好repo工具之后,添加对应权限,然后将repo添加到环境变量中。

mkdir ~/bin
sudo chmod 777 ~/bin
PATH=~/bin:$PATH
curl https://mirrors.tuna.tsinghua.edu.cn/git/git-repo > ~/bin/repo
chmod a+x ~/bin/repo
export PATH=~/bin:$PATH

三、常见异常

1)file=sys.stderr)异常
解决方案:请注意python的版本是python3而不是python2

2)mkdir: cannot create directory ‘xxx’: Permission denied

解决方案:赋予文件读写权限

sudo chmod 777 xxx

3)/usr/bin/env: ‘python’: No such file or directory
解决方案:查找python3的位置,为其创建链接

whereis python3
sudo ln -s /usr/bin/python3 /usr/bin/python

4)Cannot get https://gerrit.googlesource.com/git-repo/clone.bundle

  • 解决方案1:可以输入以下指令修改repo仓库更新的地址为国内地址,再尝试repo init
REPO_URL='https://mirrors.tuna.tsinghua.edu.cn/git/git-repo'
  • 解决方案2:还可以将如下内容复制到~/.bashrc里,这样每次系统启动都会自动修改repo仓库更新的地址为国内地址,再尝试repo init
sudo vim ~/.bashrc
export REPO_URL='https://mirrors.tuna.tsinghua.edu.cn/git/git-repo'
  • 解决方案3:直接修改~/bin/repo文件内容中REPO_URL 的赋值
#REPO_URL = os.environ.get('REPO_URL', None) //注释掉这一行,新增下面一行配置
REPO_URL = os.environ.get('REPO_URL', 'https://mirrors.tuna.tsinghua.edu.cn/git/git-repo')
if not REPO_URL:
 #REPO_URL = 'https://gerrit.googlesource.com/git-repo' //注释掉这一行,新增下面一行配置
 REPO_URL = 'https://mirrors.tuna.tsinghua.edu.cn/git/git-repo'
REPO_REV = os.environ.get('REPO_REV')
if not REPO_REV:
  REPO_REV = 'stable'
# URL to file bug reports for repo tool issues.
BUG_URL = 'https://bugs.chromium.org/p/gerrit/issues/entry?template=Repo+tool+issue'

四、使用Repo初始化仓库

1、创建Android系统源码存放目录

 mkdir /home/ubuntu/android (根据实际情况来新建目录)
 cd /home/ubuntu/android

2、初始化仓库

sudo snap install git-repo
repo init -u https://aosp.tuna.tsinghua.edu.cn/platform/manifest

五、同步源码

1、repo指定Android版本

repo init -u https://aosp.tuna.tsinghua.edu.cn/platform/manifest -b android-9.0.0_r8

2、repo指定Android版本

repo sync  (等待源代码下载完成,长时间等待,若失败请检查网络等情况)

四、搭建编译环境

1、安装openJDK8

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

2、安装依赖

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

3、 设置启用ccache (加快重新编译源码时的速度。可选)

export USE_CCACHE=1  (在你home主目录的.bashrc中加入)
export CCACHE_DIR=/home/ubuntu/.ccache  (指定一个缓存目录,也可以不指定,默认目录为你当前用户目录下的.ccache)
aosp/prebuilts/misc/linux-x86/ccache/ccache -M 50G (这个命令在Android源码中,缓存大小按照自己的硬盘来适当调整)
source ~/.bashrc  (source命令使修改立即生效)

4、下载手机驱动
1) 打开Android系统源代码标记和 build列表页面,查看源代码标记和 build版本,主要是为了后面下载对应版本的驱动。
Android9.0系统源码_编译刷机——从下载到编译_第1张图片

2)从上图可知android-9.0.0_r8系统源码对应的是buildId为PPR2.180905.006.A1,打开Android系统版本驱动列表页面,搜索关键字PPR2.180905.006.A1,找到android-9.0.0_r8对应的驱动。
Android9.0系统源码_编译刷机——从下载到编译_第2张图片
3)将下载的文件解压放在源码根目录,授权执行sh文件,运行后,会提示你查看证书,按Enter键一行行的查看,出现输入提示时,输入 I ACCEPT,解压到了vendor 目录下

./extract-google_devices-sailfish.sh
./extract-qcom-sailfish.sh

4)对于以上步骤有什么疑惑的可以参考官方文档:谷歌官网文档搭建编译环境

六、编译系统

1、设置环境
使用 envsetup.sh 脚本初始化环境。请注意,将 source 替换成 .(一个点)可以省去一些字符,这种简写形式在文档中更为常用。

source build/envsetup.sh

2、选择目标
使用 lunch 选择要编译的目标。确切的配置可作为参数进行传递。
例如,以下命令表示针对模拟器进行完整编译,并且所有调试功能均处于启用状态。

lunch aosp_arm-eng

直接运行 lunch (没有参数),会列出所有支持的类型,输入对应的序号来进行选择。
Android9.0系统源码_编译刷机——从下载到编译_第3张图片
所有编译目标都采用 BUILD-BUILDTYPE 形式,其中 BUILD 是表示特定功能组合的代号。BUILDTYPE 是以下类型之一:

user userdebug eng
仅安装标签为 user 的模块 安装标签为 user、debug 的模块 安装标签为 user、debug、eng 的模块
设定属性 ro.secure=1,打开安全检查功能 设定属性 ro.secure=1,打开安全检查功能 设定属性 ro.secure=0,关闭安全检查功能
设定属性 ro.debuggable=0,关闭应用调试功能 设定属性 ro.debuggable=1,启用应用调试功能 设定属性 ro.debuggable=1,启用应用调试功能
设定属性 ro.kernel.android.checkjni=1,启用 JNI 调用检查
默认关闭 adb 功能 默认打开 adb 功能 默认打开 adb 功能
关闭root权限 开启root权限 开启root权限
打开 Proguard 混淆器 打开 Proguard 混淆器 关闭 Proguard 混淆器
打开 DEXPREOPT 预先编译优化 打开 DEXPREOPT 预先编译优化 关闭 DEXPREOPT 预先编译优化
3、源码编译
您可以使用 make 编译任何代码。GNU make 可以借助 -j【N】 参数处理并行任务,通常使用的任务数 【N】 介于编译时所用计算机上硬件线程数的 1-2 倍之间。例如,在一台双核 E5520 计算机(2 个 CPU,每个 CPU 4 个内核,每个内核 2 个线程)上,要实现最快的编译速度,可以使用介于 make -j16 到 make -j32 之间的命令。
make -j16

如果编译完一个版本后想重新编译一个,可以使用 make clobber清除之前编译生成的文件。我们编译产生的文件都在 out文件夹下。

4、 启动模拟器
编译成功后,将镜像烧入模拟器硬件设备,就可以启动模拟器进入Android系统了

七、如何查看源码的版本

1、 从代码中查看当前版本,找到如下文件

build\core\version_defaults.mk

2、找到关键字 PLATFORM_VERSION

INTERNAL_BUILD_ID_MAKEFILE := $(wildcard $(BUILD_SYSTEM)/build_id.mk)
ifdef INTERNAL_BUILD_ID_MAKEFILE
  include $(INTERNAL_BUILD_ID_MAKEFILE)
endif

DEFAULT_PLATFORM_VERSION := PPR1
MIN_PLATFORM_VERSION := PPR1
MAX_PLATFORM_VERSION := PPR1

ALLOWED_VERSIONS := $(call allowed-platform-versions,\
  $(MIN_PLATFORM_VERSION),\
  $(MAX_PLATFORM_VERSION),\
  $(DEFAULT_PLATFORM_VERSION))

ifndef TARGET_PLATFORM_VERSION
  TARGET_PLATFORM_VERSION := $(DEFAULT_PLATFORM_VERSION)
endif

ifeq (,$(filter $(ALLOWED_VERSIONS), $(TARGET_PLATFORM_VERSION)))
  $(warning Invalid TARGET_PLATFORM_VERSION '$(TARGET_PLATFORM_VERSION)', must be one of)
  $(error $(ALLOWED_VERSIONS))
endif

PLATFORM_VERSION.PPR1 := 9

八、系统编译/模块编译

1、完整系统编译

1)进入frameworks的上一级目录
2)source build/envsetup.sh
3)lunch 选择编译的类型
4)使用make命令开始进行系统编译

2、kernel模块编译:

1)/kernel/msm-3.18/drivers/misc/qcom/leapmotor/drv_gpio/
2)进入frameworks的上一级目录
3)source build/envsetup.sh
4)lunch 选择编译的类型
5)输入make bootimage -j16命令开始进行kernel模块的编译
6)根据最终输出信息确认rawprogram-boot.xml文件的路径
7)使用QF进行boot的刷机操作

3、framework/base/services模块编译

修改了framework/base/services目录下面的类代码之后,需要重新编译产生/system/framework/services.jar文件替换原有的文件。

1)进入frameworks的上一级目录
2)source build/envsetup.sh
3)lunch 选择编译的类型
4)在当前目录输入mmm frameworks/base/services/ 或者进入frameworks/base/services目录输入mma命令进行services模块编译
5)编译完毕,services.jar文件的生成目录为:/out/target/product/msm***/system/framework
6)adb root、adb remount获取硬盘读写权限(高版本系统还需要adb disable-verity禁用分区检测)
7)使用adb push services.jar /system/framework/ 替换掉系统中旧的services.jar

4、framework/base/core/res/res模块编译

修改了framework/base/core/res/res目录下面的资源之后,需要重新编译产生/system/framework/framework-res.apk文件替换原有的文件。

1)进入frameworks的上一级目录
2)source build/envsetup.sh
3)lunch 选择编译的类型
4)进入framework/base/core/res目录
5)使用mma命令开始进行res模块的编译
6)编译完毕,framework-res.apk文件的生成目录为:/out/target/product/msm***/system/framework
7)adb root、adb remount获取硬盘读写权限(高版本系统还需要adb disable-verity禁用分区检测)
8)使用adb push services.jar /system/framework/ 替换掉系统中旧的framework-res.apk

5、frameworks/base模块编译

1)进入frameworks的上一级目录
2)source build/envsetup.sh
3)lunch 选择编译的类型
4)进入framework/base/目录
5)使用mma命令开始进行base模块的编译
6)编译完毕,framework.jar文件的生成目录为:/out/target/product/msm***/system/framework
7)adb root、adb remount获取硬盘读写权限(高版本系统还需要adb disable-verity禁用分区检测)
8)使用adb push framework.jar /system/framework/ 替换掉系统中旧的framework.jar

6、SystemUI模块编译:

修改了framework/base/packages/SystemUI目录下面的代码和资源之后,需要重新编译产生/system/priv-app/SystemUI/SystemUI.apk文件替换原有的文件。

1)进入frameworks的上一级目录
2) source build/envsetup.sh
3)lunch 选择编译的类型
4)输入mmm frameworks/base/packages/SystemUI命令开始进行SystemUI模块的编译(也可以直接在framework的上一级目录执行make SystemUI来进行SystemUI模块的编译)
5)编译完毕,根据最终输出信息确认SystemUI.apk件的路径
6)out/target/product/msm***/system/priv-app/SystemUI/SystemUI.apk
7)使用adb push SystemUI.apk /system/priv-app/SystemUI/ 替换掉系统中旧的SystemUI.apk

你可能感兴趣的:(framework9.0,android,framwroks)