共計 3568 個字符,預計需要花費 9 分鐘才能閱讀完成。
本篇內容介紹了“makefile 模塊獨立編譯的支持方法是什么”的有關知識,在實際案例的操作過程中,不少人都會遇到這樣的困境,接下來就讓丸趣 TV 小編帶領大家學習一下如何處理這些情況吧!希望大家仔細閱讀,能夠學有所成!
解決方案便是:1、將模塊名(module)作為目標名(偽目標)建立規則;2、目標(module)對應的依賴為 build build/module;3、規則中的命令進入對應的模塊文件夾進行編譯;4、編譯結果存放于 build 文件夾下。其關鍵技術點是如何獲取 make 命令行中指定編譯的模塊名,通過預定義變量:$(MAKECMDGOALS),命令行中指定的目標名(make 的命令行參數)。如下
下來我們來看看具體的 makefile 是怎樣寫的,將上節博客中的 pro-rule.mk 改成下面這樣
.PHONY : all compile link clean rebuild $(MODULES)
DIR_PROJECT := $(realpath .)
DIR_BUILD_SUB := $(addprefix $(DIR_BUILD)/, $(MODULES))
MODULE_LIB := $(addsuffix .a, $(MODULES))
MODULE_LIB := $(addprefix $(DIR_BUILD)/, $(MODULE_LIB))
APP := $(addprefix $(DIR_BUILD)/, $(APP))
all : compile $(APP)
@echo Success! Target == $(APP)
compile : $(DIR_BUILD) $(DIR_BUILD_SUB)
@echo Begin to compile ...
@set -e; \
for dir in $(MODULES); \
do \
cd $$dir \
$(MAKE) all \
DEBUG:=$(DEBUG) \
DIR_BUILD:=$(addprefix $(DIR_PROJECT)/, $(DIR_BUILD)) \
DIR_COMMON_INC:=$(addprefix $(DIR_PROJECT)/, $(DIR_COMMON_INC)) \
CMD_CFG:=$(addprefix $(DIR_PROJECT)/, $(CMD_CFG)) \
MOD_CFG:=$(addprefix $(DIR_PROJECT)/, $(MOD_CFG)) \
MOD_RULE:=$(addprefix $(DIR_PROJECT)/, $(MOD_RULE)) \
cd .. ; \
done
@echo Compile Success!
link $(APP) : $(MODULE_LIB)
@echo Begin to link ...
$(CC) -o $(APP) -Xlinker -( $^ -Xlinker -) $(LFLAGS)
@echo Link Success!
$(DIR_BUILD) $(DIR_BUILD_SUB) :
$(MKDIR) $@
clean :
@echo Begin to clean ...
$(RM) $(DIR_BUILD)
@echo Clean Success!
rebuild : clean all
$(MODULES) : $(DIR_BUILD) $(DIR_BUILD)/$(MAKECMDGOALS)
@echo Begin to compile $@
@set -e; \
for dir in $(MODULES); \
do \
cd $@ \
$(MAKE) all \
DEBUG:=$(DEBUG) \
DIR_BUILD:=$(addprefix $(DIR_PROJECT)/, $(DIR_BUILD)) \
DIR_COMMON_INC:=$(addprefix $(DIR_PROJECT)/, $(DIR_COMMON_INC)) \
CMD_CFG:=$(addprefix $(DIR_PROJECT)/, $(CMD_CFG)) \
MOD_CFG:=$(addprefix $(DIR_PROJECT)/, $(MOD_CFG)) \
MOD_RULE:=$(addprefix $(DIR_PROJECT)/, $(MOD_RULE)) \
cd .. ; \
done
@echo Compile Success!
我們來看看編譯結果
我們看到 common 模塊已經正確編譯了,而且生成相應的 common.a 文件了。我們再繼續編譯別的兩個模塊,再通過鏈接的命令看看可執行程序 app.out 是否可以生成
我們看到可執行程序 app.out 已經正確生成了。那么我們看到剛才的模塊編寫是直接復制之前的代碼,凡是涉及到復制粘貼的代碼,我們得看看是否可以封裝成類似于函數的形式。在 makefile 中的代碼復用規則是這樣的,當不同規則中的命令大量重復時,可考慮自定義函數,makefile 中的自定義函數是代碼復用的一種方式。如下
具體思路就是:1、將編譯模塊的命令作為自定義函數的具體實現;2、函數參數為模塊名,函數調用后編譯參數指定的模塊;3、在不同的規則中調用該函數。如下
下面我們看看改變后的 makefile 是怎樣的,將前面的 pro-rule.mk 改成下面這樣
.PHONY : all compile link clean rebuild $(MODULES)
DIR_PROJECT := $(realpath .)
DIR_BUILD_SUB := $(addprefix $(DIR_BUILD)/, $(MODULES))
MODULE_LIB := $(addsuffix .a, $(MODULES))
MODULE_LIB := $(addprefix $(DIR_BUILD)/, $(MODULE_LIB))
APP := $(addprefix $(DIR_BUILD)/, $(APP))
define makemodule
cd ${1} \
$(MAKE) all \
DEBUG:=$(DEBUG) \
DIR_BUILD:=$(addprefix $(DIR_PROJECT)/, $(DIR_BUILD)) \
DIR_COMMON_INC:=$(addprefix $(DIR_PROJECT)/, $(DIR_COMMON_INC)) \
CMD_CFG:=$(addprefix $(DIR_PROJECT)/, $(CMD_CFG)) \
MOD_CFG:=$(addprefix $(DIR_PROJECT)/, $(MOD_CFG)) \
MOD_RULE:=$(addprefix $(DIR_PROJECT)/, $(MOD_RULE)) \
cd .. ;
endef
all : compile $(APP)
@echo Success! Target == $(APP)
compile : $(DIR_BUILD) $(DIR_BUILD_SUB)
@echo Begin to compile ...
@set -e; \
for dir in $(MODULES); \
do \
$(call makemodule, $$dir) \
done
@echo Compile Success!
link $(APP) : $(MODULE_LIB)
@echo Begin to link ...
$(CC) -o $(APP) -Xlinker -( $^ -Xlinker -) $(LFLAGS)
@echo Link Success!
$(DIR_BUILD) $(DIR_BUILD_SUB) :
$(MKDIR) $@
clean :
@echo Begin to clean ...
$(RM) $(DIR_BUILD)
@echo Clean Success!
rebuild : clean all
$(MODULES) : $(DIR_BUILD) $(DIR_BUILD)/$(MAKECMDGOALS)
@echo Begin to compile $@
@set -e; \
$(call makemodule, $@)
編譯的結果是
“makefile 模塊獨立編譯的支持方法是什么”的內容就介紹到這里了,感謝大家的閱讀。如果想了解更多行業相關的知識可以關注丸趣 TV 網站,丸趣 TV 小編將為大家輸出更多高質量的實用文章!