通用makefile系列收视率比较惨淡,工程本身也进入尾期,这里直接大跃进喽
上类图
类图画得不好,所以下面文字简单解释
1. 整个通用makefile分为若干大块,也就是上面用包表示的部分,主要是产品Product,编译平台Platform,操作系统System,模块Module,编译目标Target,以及Build和Path这两块。
产品Product,编译平台Platform,操作系统System,编译目标Target 都是独立的组件,不依赖于module。
2. 对编译目标Target,Module可以选择加载里面的成员,excutable.mk, 或者static-library.mk, 分别表示编译生成可执行文件或者静态库。Target自身不依赖于Module(不过目前实现还是依赖于ModuleName 和ModulePath),但预留了定制接口TARGET_SPECS,Target会自动加载该变量指定的文件。
3. 对产品Product,主要的信息可以在vendor.mk 以及features.mk中定义,类似于Target, Product也提供了定制接口PRODUCT_SPECS。
特别值得一提的是Product另外提供了接口hook__import-product,该接口用于指定产品中的各项信息该如何加载以及组织。该接口的实现在Build组件的utility.mk。当前的实现是可以支持多产品的,各个产品以文件夹分类
4. 对编译平台Platform,基本同Product。 稍微有点不同的是支持多平台的方式不是通过文件夹分类,而是直接按平台名称命名,如果x86-linux.mk, arm-linux.mk等等
5. 对Path,主要负责整合各种路径问题,如obj文件的存放路径、lib文件的存放路径等等。这个组件实际是与其他组件紧密耦合的。上面图中省略了这种耦合关系。(其实将它放到包Build里面可能比较好)
6. 最终的模块module。module是一个集大成者。module.mk的实现就相当于是一个简单的makefile,具体内容包括加载操作系统信息,加载产品信息,加载编译平台信息,加载路径信息,配置自身的模块信息,调用需要的编译目标进行编译。
另外module是可以对其他模块做出定制的。以增加特性为例,如果需要为A模块单独增加某个特性,可以新建一个makefile,将特性定义在其中。然后只要定义PRODUCT_SPECS的值为刚才新建的makefile路径,一切就ok了。
7. Build模块是整体的容器,通过main.mk 加载指定的module.mk, 总共加载了几个,就编译几个。
下面以加载流程图结束
over,剩下预计还有两篇,分别是脚本化,和实际应用。