repo详解与如何更改manifest快速获取和复用AOSP代码

2024-03-04 12:18

本文主要是介绍repo详解与如何更改manifest快速获取和复用AOSP代码,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

源起

现在很多企业的网络一般都比较快, 但是有的企业却会限速, 如果需要从github和google code上面git clone大的仓库的话, 那么需要耗费的时间是很客观的,  例如从github或者google code, 或者其他托管服务站点获取Android中需要的多个Kernel仓库, 一般一个kernel仓库都有几GB, 如果是100KB/S的话, 那么将需要很长的时间.

与此同时, 不同的Android 版本(AOSP)代码, 他们一般都会依赖许多相同的组件, 甚至获取相同的仓库代码, 仅仅只是branch或者tag不同而已, 例如对于Nexus 7 flo平板而言, 不管是AOSP 4.4 Kitkat还是 5.X Lolipop, 都会去下载flo-kernel这个内核, 他们都remote都是一样的, 唯一不同的是tag使用的不同, 因此如果我们已经获取过Kitkat的代码,那么就可以复用其中的bare repo, 从而达到快速clone.

要了解如何做, 我们需要对AOSP的代码结构非常熟悉, 一般而言, 如果是系统工程师,那么几乎对AOSP的每一个目录都会很熟悉, 对自己需要编译的target的依赖的每一个repo都几乎会心中有数(例如external中的哪些, vendor, device都会用到哪些), 这种情况下, 就可以删除某些仓库的下载, 从而节省时间.

总结起来, 要节省git clone的时间就是从两个方面入手:

  • 1. 复用已经clone的bare repo
  • 2. 不要clone不需要的repo


repo分析

在实现前面的两点之前, 除了对AOSP的编译, 以及Target的依赖很熟悉外, 我们还需要对google 的 repo工具以及其流程有个基本的熟悉和了解.

repo的执行过程

  1. 解析传入的args
  2. checkout下来最新的repo
  3. 找到manifest的目录
  4. 解析manifest.xml
  5. 根据manifest或者其他xml文件调用git clone --bare-repo获取xml中定义的clone repo
  6. 从.repo/projects中的bare repo根据manifest xml中的projects信息checkout到当前目录

具体查看repo这个python脚本的源码.

下面使用具体例子来讲解.

repo init

repo init -u https://github.com/bluez-android/aosp_platform_manifest.git -b lollipop

这个init调用传入的-u这个用于指定需要下载的manifest的仓库地址: 

def _Checkout(cwd, branch, rev, quiet):"""Checkout an upstream branch into the repository and track it."""cmd = [GIT, 'update-ref', 'refs/heads/default', rev]if subprocess.Popen(cmd, cwd=cwd).wait() != 0:raise CloneFailure()_SetConfig(cwd, 'branch.default.remote', 'origin')_SetConfig(cwd, 'branch.default.merge', 'refs/heads/%s' % branch)cmd = [GIT, 'symbolic-ref', 'HEAD', 'refs/heads/default']if subprocess.Popen(cmd, cwd=cwd).wait() != 0:raise CloneFailure()cmd = [GIT, 'read-tree', '--reset', '-u']if not quiet:cmd.append('-v')cmd.append('HEAD')if subprocess.Popen(cmd, cwd=cwd).wait() != 0:raise CloneFailure()


例如前面的 init 执行完成后, 我们可以看到在.repo目录下有一个manifest.git目录:

$ cd .repo/manifests.git/$ git remote -v
origin	https://github.com/bluez-android/aosp_platform_manifest.git (fetch)
origin	https://github.com/bluez-android/aosp_platform_manifest.git (push)

注意这个manifest.git属于bare repo , 然后repo会checkout一份出来manifest working tree到manifest目录, 且使用的就是前面repo init中的-b指定的branch:

.repo/manifests$ git status
On branch default
Your branch is up-to-date with 'origin/lollipop'. // branch -b指定后在这里

然后我们可以看到有一个manifest.xml会指向checkout的working tree中的xml:

cd /Dir/Contain/.repo/../

$ ls -l
total 12
drwxrwxr-x  3 hexiongjun hexiongjun 4096 Feb 15 10:57 manifests // 从下面这个bare repo checkout
drwxrwxr-x 10 hexiongjun hexiongjun 4096 Feb 15 10:54 manifests.git  //bare repo
lrwxrwxrwx  1 hexiongjun hexiongjun   21 Feb 15 10:40 manifest.xml -> manifests/default.xml
drwxrwxr-x  7 hexiongjun hexiongjun 4096 Feb 15 10:40 repo // repo本身的working tree checkout

repo本身的checkout

在repo init执行的时候会到: https://gerrit.googlesource.com/git-repo

checkout最新的repo, checkout下来后放在了.repo/repo目录


manifest的修改

前面的ls -l命令中列出了manifest.xml指向的是manifests/default.xml, 然后这个xml中会指明各种fetch的url, 版本revision, 以及需要checkout下来的projects, 例如:

<?xml version="1.0" encoding="UTF-8"?>
<manifest><remote  name="aosp"fetch=".." /><default revision="refs/tags/android-5.0.0_r7"remote="aosp"sync-j="4" /><project path="build" name="platform/build" groups="pdk,tradefed" ><copyfile src="core/root.mk" dest="Makefile" /></project><project path="abi/cpp" name="platform/abi/cpp" groups="pdk" /><project path="art" name="platform/art" groups="pdk" />
.............<include name="bluez-android.xml" /></manifest>


里面的remote就是git remote获取得到的remote name, fetch指定的是从哪里checkout projects, 随后指定了revision, 以及sync的并心数.

接下来是projects的list, path指定checkout下来后放到哪里, 例如下面这行:

  <project path="device/htc/flounder-kernel" name="device/htc/flounder-kernel" groups="device,flounder" clone-depth="1" />

指定了从fetch/name这个位置clone, 因为repo本身会将所有的projects放到.repo/projects目录下面, 这个存放的位置就是由后面的groups来指定的, 例如上面的flounder-kernel的repo 本地bare repo位于:

.repo/projects/device/flounder-kernel.git

而这个repository的objects则位于:

.repo/project-objects/aosp_device_asus_flo-kernel.git/

这个objects目录大小为:

$ du -sh ../../project-objects/aosp_device_asus_flo-kernel.git/
1.2G	../../project-objects/aosp_device_asus_flo-kernel.git/


然后repo在为每一个project建立了bare repository之后, 会从本地使用git clone一份出来, 且版本为前面指定的revision.


最后xml还可以使用include来包含, 实现"重载"


了解了repo的工作过程后,我们就可以想办法来重用以前的bare repository了, 也知道如何不去clone和建立不需要的project的bare repository.


如何重用已有的bare repo仓库来加快clone

假设我们已经有了一个AOSP 4.4 Kitkat的flo-kernel的bare repository了, 而AOSP 5.1 Lollipop也需要fetch 这个project,那么我们就可以按照下面这个方式来做.

1. 拷贝project objects到对应目录

2. 拷贝projects下的对应目录到新的需要checkout的目录, 例如从AOSP4到5

然后直接repo sync, sync完成后, 我们可以看到对应的branch被重新checkout下来了:

$ git branch  -aremotes/github/kitkatremotes/github/lollipopremotes/m/kitkat -> github/kitkatremotes/m/lollipop -> github/lollipop
可以看到既有kitkat也有lollipop, 这个和我们期望的一致:

  <project path="device/asus/flo-kernel" name="aosp_device_asus_flo-kernel" groups="device,flo" revision="lollipop" remote="github" />

这个xml中的project还指定了路径, 我们到里面确定一下:

 cd ../device/asus/flo-kernel/$ git branch  -a
* (no branch)remotes/github/kitkatremotes/github/lollipopremotes/m/kitkat -> github/kitkatremotes/m/lollipop -> github/lollipop

然后我们使用gitk看看, 可以确定是我们需要的branch中:



删除不需要的代码仓库

例如我们使用的Nexus 7 flo来做开发, 并不需要Nexus 9等其他的内核, 那么可以直接在xml中注释掉其他的, repo就不会去下载了:



如果后来又需要checkout这些仓库,那么取消注释, 然后重新repo sync即可.

也可以使用remove-project指定, 如同上图中的前面几行.

其他的例如drawn, MIPS等一些用不到的仓库也可以删除掉.

这篇关于repo详解与如何更改manifest快速获取和复用AOSP代码的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/773146

相关文章

乐鑫 Matter 技术体验日|快速落地 Matter 产品,引领智能家居生态新发展

随着 Matter 协议的推广和普及,智能家居行业正迎来新的发展机遇,众多厂商纷纷投身于 Matter 产品的研发与验证。然而,开发者普遍面临技术门槛高、认证流程繁琐、生产管理复杂等诸多挑战。  乐鑫信息科技 (688018.SH) 凭借深厚的研发实力与行业洞察力,推出了全面的 Matter 解决方案,包含基于乐鑫 SoC 的 Matter 硬件平台、基于开源 ESP-Matter SDK 的一

uniapp接入微信小程序原生代码配置方案(优化版)

uniapp项目需要把微信小程序原生语法的功能代码嵌套过来,无需把原生代码转换为uniapp,可以配置拷贝的方式集成过来 1、拷贝代码包到src目录 2、vue.config.js中配置原生代码包直接拷贝到编译目录中 3、pages.json中配置分包目录,原生入口组件的路径 4、manifest.json中配置分包,使用原生组件 5、需要把原生代码包里的页面修改成组件的方

公共筛选组件(二次封装antd)支持代码提示

如果项目是基于antd组件库为基础搭建,可使用此公共筛选组件 使用到的库 npm i antdnpm i lodash-esnpm i @types/lodash-es -D /components/CommonSearch index.tsx import React from 'react';import { Button, Card, Form } from 'antd'

17.用300行代码手写初体验Spring V1.0版本

1.1.课程目标 1、了解看源码最有效的方式,先猜测后验证,不要一开始就去调试代码。 2、浓缩就是精华,用 300行最简洁的代码 提炼Spring的基本设计思想。 3、掌握Spring框架的基本脉络。 1.2.内容定位 1、 具有1年以上的SpringMVC使用经验。 2、 希望深入了解Spring源码的人群,对 Spring有一个整体的宏观感受。 3、 全程手写实现SpringM

十四、观察者模式与访问者模式详解

21.观察者模式 21.1.课程目标 1、 掌握观察者模式和访问者模式的应用场景。 2、 掌握观察者模式在具体业务场景中的应用。 3、 了解访问者模式的双分派。 4、 观察者模式和访问者模式的优、缺点。 21.2.内容定位 1、 有 Swing开发经验的人群更容易理解观察者模式。 2、 访问者模式被称为最复杂的设计模式。 21.3.观察者模式 观 察 者 模 式 ( Obser

【操作系统】信号Signal超详解|捕捉函数

🔥博客主页: 我要成为C++领域大神🎥系列专栏:【C++核心编程】 【计算机网络】 【Linux编程】 【操作系统】 ❤️感谢大家点赞👍收藏⭐评论✍️ 本博客致力于知识分享,与更多的人进行学习交流 ​ 如何触发信号 信号是Linux下的经典技术,一般操作系统利用信号杀死违规进程,典型进程干预手段,信号除了杀死进程外也可以挂起进程 kill -l 查看系统支持的信号

Jitter Injection详解

一、定义与作用 Jitter Injection,即抖动注入,是一种在通信系统中人为地添加抖动的技术。该技术通过在发送端对数据包进行延迟和抖动调整,以实现对整个通信系统的时延和抖动的控制。其主要作用包括: 改善传输质量:通过调整数据包的时延和抖动,可以有效地降低误码率,提高数据传输的可靠性。均衡网络负载:通过对不同的数据流进行不同程度的抖动注入,可以实现网络资源的合理分配,提高整体传输效率。增

代码随想录算法训练营:12/60

非科班学习算法day12 | LeetCode150:逆波兰表达式 ,Leetcode239: 滑动窗口最大值  目录 介绍 一、基础概念补充: 1.c++字符串转为数字 1. std::stoi, std::stol, std::stoll, std::stoul, std::stoull(最常用) 2. std::stringstream 3. std::atoi, std

记录AS混淆代码模板

开启混淆得先在build.gradle文件中把 minifyEnabled false改成true,以及shrinkResources true//去除无用的resource文件 这些是写在proguard-rules.pro文件内的 指定代码的压缩级别 -optimizationpasses 5 包明不混合大小写 -dontusemixedcaseclassnames 不去忽略非公共

Steam邮件推送内容有哪些?配置教程详解!

Steam邮件推送功能是否安全?如何个性化邮件推送内容? Steam作为全球最大的数字游戏分发平台之一,不仅提供了海量的游戏资源,还通过邮件推送为用户提供最新的游戏信息、促销活动和个性化推荐。AokSend将详细介绍Steam邮件推送的主要内容。 Steam邮件推送:促销优惠 每当平台举办大型促销活动,如夏季促销、冬季促销、黑色星期五等,用户都会收到邮件通知。这些邮件详细列出了打折游戏、