如何在 Ubuntu 16.04 上构建安卓 ROM

介绍

[Android] (https://www.android.com/)是当今世界最受欢迎的操作系统. 数百个不同的原始设备制造商,即OEMs,选择在他们的设备上安装,因为它是免费的,开源的,并拥有围绕它而建的应用和服务的巨大生态系统. 不幸的是,许多OEM并不定期为Android提供超空(OTA)更新. 而其他的OEMs只在设备发射后提供有限的更新时间. 此外,OEMs还倾向于对Android进行广泛的定制,以确保它们的设备能运动出独特的外观和感受. 他们的定制包括替代发射器,主题系统用户界面,以及预先安装的应用软件.

如果你想删除所有这些定制,或者如果你想在你的设备上运行纯 Android 的最新版本,你可以为它自己构建新的固件。

在本教程中,您将构建基于 Android 开源项目的 Android Oreo ROM,或简而言之为 AOSP。

前提条件

为了能够跟随,你将需要:

步骤1 - 启动屏幕会话

在这个教程中您将执行的一些命令有可能运行数小时. 如果您的PC和服务器之间的SSH连接在命令运行时被中断,它们就会被突然终止. 为避免这种情况,使用 " 屏幕 " 工具,使您可以在一个终端上运行多个控制台会话。 通过屏幕,您可以从运行的会话中解析出来,并在稍后重新接上. 如果您是新来屏幕的, 请在 [这个在 Ubuntu 上使用屏幕的教程] (https://andsky.com/tech/tutorials/how-to-install-and-use-screen-on-an-ubuntu-cloud-server) 中学习更多 .

开始一个新的屏幕会话。

1screen

当您第一次运行屏幕时,您将收到许可协议. 按 Enter 以接受许可证。

从此开始,如果您的 SSH 连接失败,您的长期运行命令将继续在背景中运行.一旦您重新建立 SSH 连接,您将能够通过运行屏幕 -r来恢复会话。

接下来,让我们安装我们需要编译 Android 的组件。

第2步:安装依赖性

AOSP 源代码分布在多个不同的 Git 存储库中,为了让用户更容易地下载所有这些存储库,AOSP 社区创建了一个命令行工具,名为 repo

我们将使用wget下载工具的最新版本,并将其存储在~/bin目录中,首先创建~/bin目录:

1mkdir -p ~/bin

然后下载repo脚本:

1wget 'https://storage.googleapis.com/git-repo-downloads/repo' -P ~/bin

注:如果您担心您从其他网站下载的脚本在您的机器上运行的安全性,请检查脚本的内容:

1less ~/bin/repo

一旦您对脚本的内容感到满意,请继续使用本教程。

使用chmod授予当前用户运行repo的权限。

1chmod +x ~/bin/repo

repo工具使用Git内部,并要求您创建一个Git配置,指定您的用户名和电子邮件地址。

1git config --global user.name "your name"
2git config --global user.email "your_email@your_domain.com"

Android的源代码主要由Java,C++和XML文件组成,要编译源代码,您需要安装OpenJDK 8,GNU C和C++编译器,XML分析库,ImageMagick和其他几个相关包。

1sudo apt-get update

一旦列表更新,安装依赖:

1sudo apt-get install openjdk-8-jdk android-tools-adb bc bison build-essential curl flex g++-multilib gcc-multilib gnupg gperf imagemagick lib32ncurses5-dev lib32readline-dev lib32z1-dev libesd0-dev liblz4-tool libncurses5-dev libsdl1.2-dev libssl-dev libwxgtk3.0-dev libxml2 libxml2-utils lzop pngcrush rsync schedtool squashfs-tools xsltproc yasm zip zlib1g-dev

一旦依赖性下载,我们可以使用repo脚本来获取Android源。

第3步:下载源代码

我们将使用repo脚本来完成几个任务来准备我们的工作空间,创建一个新的目录来存储你要下载的Android源:

1mkdir -p ~/aosp/oreo

您将在本教程的剩余时间内在这个目录中工作,所以现在切换到它:

1cd ~/aosp/oreo

该目录必须与AOSP( manifesto repository)(LINK0)初始化,这是一个包含一个名为default.xml的XML文件的特殊Git repository,它指定了组成AOSP代码库的所有其他Git repository的路径。

在本教程中,因为我们正在构建Oreo ROM,我们将使用Android-8.0.0_r33分支,其构建ID是OPD1.170816.025

此外,您将不需要这个教程的代码树的整个承诺历史记录,您可以节省时间和存储空间,将历史记录缩小到1的深度。

因此,使用repo init命令来初始化目录并指定这些选项:

1repo init -u https://android.googlesource.com/platform/manifest -b android-8.0.0_r33 --depth=1

当被提示启用彩色显示时,按 Y ,然后按 ** Enter** 。

最后,从各种存储库下载实际的 AOSP 文件,运行repo sync命令:

1repo sync

上面的命令下载超过 30 GB 的数据,所以在完成时要耐心。

步骤4 – 准备一个编译器缓存

要加快构建速度,您可以使用编译器缓存,正如其名称所示,编译器缓存可以帮助您避免重新编译已编译的ROM部分。

要启用编译器缓存,设置一个名为USE_CCACHE的环境变量。

1export USE_CCACHE=1

除非您有大量的自由磁盘空间,否则您不希望缓存太大,因此您可以限制其大小;如果您正在为单个设备构建您的ROM,您可以将其限制到15 GB。

1prebuilts/misc/linux-x86/ccache/ccache -M 15G

您将看到确认您已执行此更改的输出:

1[secondary_label Output]
2Set cache size limit to 15.0 Gbytes

在我们可以编译之前,我们还需要进行一项优化。

第5步:设置Jack

Jack 服务器,负责构建 ROM 基于 Java 的大部分部分,需要大量的内存。为了避免内存分配错误,您可以使用名为ANDROID_JACK_VM_ARGS的环境变量来指定允许使用内存 Jack 的数量。

执行以下命令,将 8 GB 的 RAM 分配给 Jack 服务器,并保留 Jack 需要的默认编译选项:

1export ANDROID_JACK_VM_ARGS="-Xmx8g -Dfile.encoding=UTF-8 -XX:+TieredCompilation"

现在你已经准备好构建你的Android ROM了。

步骤6 - 开始构建

AOSP代码树包含一个名为envsetup.sh的脚本,该脚本具有几个与构建相关的辅助函数,而许多辅助函数,如mm,mmammm,作为命令的捷径,其他人,如午餐设置了重要的环境变量,这些变量,包括决定ROM的CPU架构,以及构建的类型。

源脚本,以获取访问辅助函数。

1source build/envsetup.sh
 1[secondary_label Output]
 2including device/asus/fugu/vendorsetup.sh
 3including device/generic/car/car-arm64/vendorsetup.sh
 4including device/generic/car/car-armv7-a-neon/vendorsetup.sh
 5including device/generic/car/car-x86_64/vendorsetup.sh
 6including device/generic/car/car-x86/vendorsetup.sh
 7including device/generic/mini-emulator-arm64/vendorsetup.sh
 8including device/generic/mini-emulator-armv7-a-neon/vendorsetup.sh
 9including device/generic/mini-emulator-mips64/vendorsetup.sh
10including device/generic/mini-emulator-mips/vendorsetup.sh
11including device/generic/mini-emulator-x86_64/vendorsetup.sh
12including device/generic/mini-emulator-x86/vendorsetup.sh
13including device/google/dragon/vendorsetup.sh
14including device/google/marlin/vendorsetup.sh
15including device/google/muskie/vendorsetup.sh
16including device/google/taimen/vendorsetup.sh
17including device/huawei/angler/vendorsetup.sh
18including device/lge/bullhead/vendorsetup.sh
19including device/linaro/hikey/vendorsetup.sh
20including sdk/bash_completion/adb.bash

接下来,运行午餐并将设备的代码名称传递给它,附带一个构建类型,可以是eng,userdebug用户

要构建可在 AOSP ARM 模拟器上运行的试用 ROM,请将aosp_arm-eng传输到午餐命令:

1lunch aosp_arm-eng

您将看到此输出,显示环境设置:

 1[secondary_label Output]
 2============================================
 3PLATFORM_VERSION_CODENAME=REL
 4PLATFORM_VERSION=8.0.0
 5TARGET_PRODUCT=aosp_arm
 6TARGET_BUILD_VARIANT=eng
 7TARGET_BUILD_TYPE=release
 8TARGET_PLATFORM_VERSION=OPD1
 9TARGET_BUILD_APPS=
10TARGET_ARCH=arm
11TARGET_ARCH_VARIANT=armv7-a
12TARGET_CPU_VARIANT=generic
13TARGET_2ND_ARCH=
14TARGET_2ND_ARCH_VARIANT=
15TARGET_2ND_CPU_VARIANT=
16HOST_ARCH=x86_64
17HOST_2ND_ARCH=x86
18HOST_OS=linux
19HOST_OS_EXTRA=Linux-4.4.0-104-generic-x86_64-with-Ubuntu-16.04-xenial
20HOST_CROSS_OS=windows
21HOST_CROSS_ARCH=x86
22HOST_CROSS_2ND_ARCH=x86_64
23HOST_BUILD_TYPE=release
24BUILD_ID=OPD1.170816.025
25OUT_DIR=out
26AUX_OS_VARIANT_LIST=
27============================================

最后,运行来启动构建。支持并行任务,因此您可以通过使用-j选项将并行任务的数量设置为服务器中可用的CPU数量来大大加速构建。

使用nproc命令查看您有多少CPU:

1nproc

该命令返回 CPUS 号码:

1[secondary_label Output]
28

然后,您可以使用这个数字与来指定并行执行:

1make -j8

即使有 8 个 CPU,您也需要等待超过一个小时才能完成构建,只要您的服务器上没有其他 CPU 密集的流程。构建的持续时间与您所拥有的 RAM 和 CPU 数量直接相比例。

注意:你会看到许多在构建过程中生成的警告消息,你可以安全地忽略它们。

一旦 ROM 准备好了,你应该看到一个消息,说明构建成功完成,你也可以看到构建的确切持续时间。

 1[secondary_label Output]
 2...
 3Creating filesystem with parameters:
 4    Size: 2147483648
 5    Block size: 4096
 6    Blocks per group: 32768
 7    Inodes per group: 8192
 8    Inode size: 256
 9    Journal blocks: 8192
10    Label: system
11    Blocks: 524288
12    Block groups: 16
13    Reserved block group size: 127
14Created filesystem with 2266/131072 inodes and 178244/524288 blocks
15[100% 63193/63193] Install system fs i... out/target/product/generic/system.img
16out/target/product/generic/system.img+ maxsize=2192446080 blocksize=2112 total=2147483648 reserve=22146432
17
18#### make completed successfully (01:05:44 (hh:mm:ss)) ####

让我们看看这些东西是正确建造的。

步骤7 - 验证构建

构建过程的输出由多个文件系统图像组成,这些图像一起构成ROM,您可以在out/target/product/generic/目录中找到它们。

1ls -l out/target/product/generic/*.img
1[secondary_label Output]
2-rw-r--r-- 1 sammy sammy 69206016 Jan 5 18:51 out/target/product/generic/cache.img
3-rw-rw-r-- 1 sammy sammy 1699731 Jan 5 19:09 out/target/product/generic/ramdisk.img
4-rw-r--r-- 1 sammy sammy 2147483648 Jan 5 19:10 out/target/product/generic/system.img
5-rw-r--r-- 1 sammy sammy 576716800 Jan 5 19:09 out/target/product/generic/userdata.img

要测试ROM,您可以尝试通过运行模拟器命令启动一个模拟器,如果您处于非GUI环境中,请确保您将无窗口无声音旗帜传递给它。

1emulator -no-window -noaudio > /dev/null 2>&1 &

要检查模拟器是否成功启动,请等待一分钟,然后使用 Android 调试桥工具adb打开模拟器上的壳。

1adb shell

如果ROM没有问题,你会看到一个从模拟器上运行的壳的提示。

1[secondary_label Output]
2* daemon not running; starting now at tcp:5037
3* daemon started successfully
4generic:/ #

输出此壳,键入输出并按ENTER,或按CTRL+D

注意: 如果您尝试在模拟器启动之前打开壳,则会看到错误消息,通知您模拟器已离线。

解决问题

如果你的构建失败了,最有可能的原因是内存不足. 要修复它,先用以下命令杀死Jack服务器:

1jack-admin kill-server

然后重新开始构建,但允许更少的并行工作. 例如,以下是如何将并行工作数量减少到 2:

1make -j2

如果您的构建由于磁盘空间不足而失败,您可能正在尝试多次构建而不清除以前的构建的结果。

1make clobber

或者,您可以通过使用 DigitalOcean 的 Block Storage来添加更多的磁盘空间。

结论

在本教程中,您成功地为 Android Oreo 构建了基于 AOSP 的 ROM. 今天您学到的技术也适用于 AOSP 的所有叉子,例如 Lineage OSResurrection Remix OS

要了解有关构建 AOSP 源代码的更多信息,请浏览 Google 组的 Android 构建论坛

Published At
Categories with 技术
comments powered by Disqus