来源:
http://blog.****.net/shift_wwx/article/details/78951896
前言:
最近碰到一个问题,公司内部的app需要替换源生的app,也就是说不编译源生的app,而编译后的out下只能由公司指定的app,没有源生的app。例如,源生的Launcher2。
网上搜了一下,并没有多少相关的文章,后来就此问题研究了一下,这里做个总结,如果有哪里不对的请不吝赐教。
对于这个问题,有三种解决方案:
1、直接删掉Launcher2这个目录方案
2、Android中源生给出的替换方案
3、统一管理方案
1、直接删掉Launcher2这个目录方案
这是个暴力的解决办法,但是移植性、维护性差一些。如果有的板卡需要,有的不需要,这样就不能删除了。
这个方案有利有弊,结合工程管理方便来。
2、Android中源生给出的替换方案
这个方案Android源生是存在的,仔细看下build/core/*.mk 就会发现有个变量叫LOCAL_OVERRIDES_PACKAGES
这个变量跟LOCAL_PACKAGE_NAME一样,在app的Android.mk中添加需要替换掉什么app(让此app不参与编译)只需要设定这个变量即可。
例如,
这里设定好LOCAL_OVERRIDES_PACKAGES 就可以让Launcher2不参与编译。
3、统一管理方案
对于第2点的方案似乎已经达到目的了,但是如果不是替换,而是简单的控制不让其参与编译,这个变量是无法设定的。来看下这里统一管理的方案,在Android中的makefile中有个变量PRODUCT_PACKAGES,这个变量是控制模块是否参与编译,我们在device目录下看到很多这样的设定,这时候如果为了项目或者板卡维护,直接修改device下的PRODUCT_PACKAGES变量就可以了。但是有时候会看到有些模块不是在device下面控制,而是放在了build下面,这个时候为了项目维护性,不能直接修改build下的变量。
有了这样的顾虑,为了以后项目维护性,想了一个办法,那就是用一个变量统一管理,以后不管是什么项目不需要源生的或者device下面已经设定好的PRODUCT_PACKAGES,只需要设定这个变量就可以了。
首先来看下PRODUCT_PACKAGES是怎么使用的。
在build/core/product.mk中看到这样的一个变量:
在makefile 中会将定义PRODUCT_PACKAGES的makefile通过 inherit-product或者 inherit-product-if-exists的函数传入。
来看下 inherit-product 函数:
首先,通过normalize-paths 确定想要的path,这个函数最终调用的是一个python脚本,感兴趣可以跟一下。
接着,将_product_var_list中定义的字符串中每个子串为名字的变量后面加上后缀,这个后缀就是需要inherit的makefile的路径。
例如,这个makefile的路径为device/common/hehe.mk,那最后变量的后面会加上@inherit:device/common/hehe.mk,表示该变量继承自哪里。
从这里看,以后PRODUCT_PACKAGES这个变量后面会跟很多mk
第3步,将变量PRODUCTS.$(strip $(word 1,$(_include_stack))).INHERITS_FROM 加入inherit的makefile的路径(这里为device/common/hehe.mk)排序后重新赋值。
第4步,最后统一为ALL_PRODUCTS。
这其中有个地方需要另外研究,就是变量 _include_stack,详细看build/core/node_fns.mk 中的处理部分。
函数inherit-product-if-exists:
这个函数会先判断inherit的makefile 是否存在。
上面只是前期的准备工作,主要的解析是在函数import-products中
这里就不详细说明,有兴趣可以看下build/core/node_fns.mk 中的过程。
最终在main.mk中会做一个过滤:
上面的第2点就是这样来的,详细第2点的解析可以看下package.mk中的运行过程。
所以,最后如果想要达到统一的管理,可以在这里做一个过滤,用一个变量统一管理。
假定这个变量的名字为PRODUCT_DEL_PACKAGES,表示需要删掉的module,那添加后的过滤代码为:
添加后编译就会把不需要编译的module去掉。
当然,这个变量是需要跟PRODUCT_PACKAGES添加到 _product_var_list 中,详细看 build/core/product.mk中:
Android 的build 过程比较复杂,这里只针对这3中办法做个简单的总结,后期后持续总结build下编译过程。请大神不吝赐教。
参考:
http://blog.****.net/lewif/article/details/50014827