You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

GNU Makefile使用eval函数引入子makefile时输出异常如何解决

问题根源
  • 配方(目标下的执行语句)中的变量默认是执行阶段延迟展开的,你用了全局的SRC变量存储每个模块的源文件,后续循环对SRC的修改会覆盖之前的值,所有目标执行时都会取最终的SRC值,而非定义目标时对应模块的SRC值。
  • foreach的循环变量名和被遍历的列表变量同名(都叫TEST_PROGRAM),会覆盖原始的测试程序列表,导致遍历逻辑异常。
  • 你用了-include引入子Makefile,加了减号后如果对应路径的子Makefile不存在,Make会直接忽略错误不会提示,导致对应模块的SRC没有被重新赋值,复用了之前模块的SRC值,这也是你第二个模块输出ABC、第三个模块输出DAB和预期不符的直接原因。
解决方法
  1. 给每个模块目标绑定目标专属变量,将当前模块的SRC值固定到对应目标上,不受后续全局SRC修改的影响。
  2. 修改foreach的循环变量名,避免和被遍历的列表变量重名。
  3. 临时把-include改成include调试,确认每个模块对应的子Makefile路径正确、存在,调试完成后可以根据需求改回-include。
  4. 确认各子Makefile的赋值符合预期:unit-tests/AnotherSampleFileToUT/Makefile中赋值SRC += DAB,unit-tests/None/Makefile中不赋值SRC或者显式写SRC :=。

注意:Makefile中目标对应的执行语句(recipe)必须以Tab字符开头,不能使用空格缩进,否则会触发语法错误。

修改后完整代码
SRC :=

include unit-tests/makefile
define COLLECT_TEST_PROGRAMS
# 每次处理新模块先清空SRC
SRC :=

# 引入当前模块的Makefile,调试阶段可以把-去掉排查文件存在性问题
-include unit-tests/$(1)/Makefile

# 给当前目标绑定专属的SRC变量,固定当前的SRC值
$(1): SRC := $(SRC)
$(1):
	@/bin/echo
	@echo The Module is $(1)
	@/bin/echo $(SRC)

Compile += $(1)
endef #COLLECT_TEST_PROGRAMS

# 循环变量改用prog,避免和原列表TEST_PROGRAM重名
$(foreach prog,$(TEST_PROGRAM),$(eval $(call COLLECT_TEST_PROGRAMS,$(prog))) )

all: $(Compile)
	@/bin/echo
	@/bin/echo Compiled Programs: $(Compile)

内容的提问来源于stack exchange,提问作者Teodor Iksinski

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 03:12:02