本文所指大型三方源代码是指如手机厂商所接收到的来自各大芯片厂商的 Android 系统代码(非 app)。这类代码的特点:
不论代码以什么形式输入,仅从代码量巨大的角度上来看,如果我们只是简单接收并通过单库来管理的话,后期或多或少会遇到一些无从下手的问题,例如:
要解决这类问题,拆库处理是比较简单易行且有效的处理方式。推荐转换成 Android 官方结构形式,通过 repo 来批量管理。以下转换及同步方法都是基于此来说明的。
另,本文虽然着眼于 Android 系统代码,但笔者认为,其它非 Android 系统代码,如果代码量很大的话,也可以考虑拆库处理。
根据 Android 官方代码库结构,整理出 manifest.xml 文件。这里根据不同厂商的管理方式不同,会有部分差异,但因为都是基于 Android 的,所以结构上的差异会非常小,很容易就能整理出来。
如果厂商本身就是使用标准 Android 方式管理的,那只需从厂商处获取原生的 manifest.xml 文件,稍加修改,变成结合我们自己的 gerrit 服务器地址和我们定义的分支就行。
如果厂商并没有这样的 xml 文件,我们则需要自己根据 Android 官方的 xml 文件以及厂商提供的代码路径结构来构造这个 xml 文件。这个构造过程并不会很复杂,上面已说,不同厂商基于 Android 的代码结构上的差异会非常小,一般都是因自身芯片而单独添加了部分库,用脚本查询、比较、处理之后,一般就能自动生成 95% 以上的结构,差异部分提取出来再单独处理即可。
根据内部的管理需求不同,可根据厂商的不同加一层顶级目录区分来自不同厂商的代码库;也可以只添加差异库,其它共库并以分支区分。像笔者这种强迫症加完美主义精神,就比较喜欢后者。
关于这些分支之间应该采用 merge 还是 rebase 的方式,可自行考虑,此处不展开细说。此处关于分支模型的说明也仅是一个建议。
此处仅说明第三方提供的代码如何完整地进入到我们的 upstream 分支。
根据代码输入形式的不同,我们可以选择是否保留第三方的完整提交记录。例如厂商交付的代码是 “Android 官方结构的多 git 库 repo 管理的且带历史版本信息的代码” 时,我们可以选择按照厂商的管理方式来管理,并可选择保留他们的历史提交记录(提示:git fetch && git merge);其它形式交付的代码一般都不会有历史提交记录,只需要把代码完整拷贝并提交到 upstream 分支即可。
不过就笔者曾经趟过的坑,提醒一下,拷贝时需格外注意软链接问题,确保在完成同步后下载下来的代码软链接也是正常展示的。另可能会有一些管理比较混乱的芯片厂商,输出的代码可能是他们某次编译之后的不干净的代码,这种时候还得我们编译验证之后才能确定同步是否正确,并在下次同步之前与对方沟通好如何提供满足我们需求的代码。这期间可能还会有其它五花八门的情况发生,需要 SCM 甄别处理。