Makefile 条件指令
Makefile Conditionals directives
以下是 Make 文件的片段:
生成文件 1:
bar = true
foo = bar
ifdef $(foo)
frobozz = yes
endif
all = ; @echo The value of frobozz is $(frobozz)
生成文件 2:
bar =
foo = $(bar)
ifdef foo
frobozz = yes
else
frobozz = no
endif
all = ; @echo The value of frobozz is $(frobozz)
在这两种情况下,输出是相同的"yes"。
所以我得出的结论是:
- 在第一种情况下,ifdef 的参数是 $(foo),最终变成 bar 意味着语句实际上看起来像 ifdef bar,所以 bar 的值被检查了。
- 在第二种情况下,ifdef 的参数直接是 foo,因此检查 foo 的值,因此语句 ifdef 检查 foo 的值,即 $(bar)。
首先我想知道我是正确理解还是理解错误。
如果我得到的是正确的,那么在第二种情况下 bar 的值是空的,所以它应该给出 no 而不是 yes .
请澄清...谢谢。
- Makefile1
首先,请注意,根据您的分配,foo 设置为 bar 而不是 true,但如果您想在 foo 中保存的不是 bar 的值,而是变量的名称 bar 本身。
然后,请注意 ifdef $(foo) 指令实际上并不适用于变量 foo 本身,而是适用于将在扩展 $(foo) 后生成,因为该指令的语法是 ifdef < variable_name >。在你的情况下 ifdef $(foo) 将等同于 ifdef bar。
- Makefile2
ifdef 不扩展变量以查看该值是否为非空,仅测试变量是否具有值。所以,
If I am getting it correctly then the value of bar in second case is
empty so it should give no rather than giving yes.
不正确。值为空,但它有值。
Consequently, tests using ifdef return true for all definitions except
those like foo =. To test for an empty value, use ifeq ($(foo),)
来自 here。
所以,对于 ifdef,foo 和 bar 之间存在差异,我们可以从下面的实验看:
bar=
foo=$(bar)
$(warning origin=$(origin foo), flavor=$(flavor foo), value="$(value foo)")
$(warning origin=$(origin bar), flavor=$(flavor bar), value="$(value bar)")
ifdef foo
$(warning foo defined)
else
$(warning foo is not defined)
endif
ifdef $(bar)
$(warning bar defined)
else
$(warning bar is not defined)
endif
输出:
Makefile:3: origin=file, flavor=recursive, value="$(bar)"
Makefile:4: origin=file, flavor=recursive, value=""
Makefile:7: foo defined
Makefile:15: bar is not defined
然而,你可以强制扩展只需要一点点改变:在分配变量 foo 时添加冒号:foo:=$(bar),两者都不会被定义:
Makefile:3: origin=file, flavor=simple, value=""
Makefile:4: origin=file, flavor=recursive, value=""
Makefile:9: foo is not defined
Makefile:15: bar is not defined
以下是 Make 文件的片段: 生成文件 1:
bar = true
foo = bar
ifdef $(foo)
frobozz = yes
endif
all = ; @echo The value of frobozz is $(frobozz)
生成文件 2:
bar =
foo = $(bar)
ifdef foo
frobozz = yes
else
frobozz = no
endif
all = ; @echo The value of frobozz is $(frobozz)
在这两种情况下,输出是相同的"yes"。
所以我得出的结论是:
- 在第一种情况下,ifdef 的参数是 $(foo),最终变成 bar 意味着语句实际上看起来像 ifdef bar,所以 bar 的值被检查了。
- 在第二种情况下,ifdef 的参数直接是 foo,因此检查 foo 的值,因此语句 ifdef 检查 foo 的值,即 $(bar)。
首先我想知道我是正确理解还是理解错误。
如果我得到的是正确的,那么在第二种情况下 bar 的值是空的,所以它应该给出 no 而不是 yes . 请澄清...谢谢。
- Makefile1
首先,请注意,根据您的分配,foo 设置为 bar 而不是 true,但如果您想在 foo 中保存的不是 bar 的值,而是变量的名称 bar 本身。
然后,请注意 ifdef $(foo) 指令实际上并不适用于变量 foo 本身,而是适用于将在扩展 $(foo) 后生成,因为该指令的语法是 ifdef < variable_name >。在你的情况下 ifdef $(foo) 将等同于 ifdef bar。
- Makefile2
ifdef 不扩展变量以查看该值是否为非空,仅测试变量是否具有值。所以,
If I am getting it correctly then the value of bar in second case is empty so it should give no rather than giving yes.
不正确。值为空,但它有值。
Consequently, tests using ifdef return true for all definitions except those like foo =. To test for an empty value, use ifeq ($(foo),)
来自 here。
所以,对于 ifdef,foo 和 bar 之间存在差异,我们可以从下面的实验看:
bar=
foo=$(bar)
$(warning origin=$(origin foo), flavor=$(flavor foo), value="$(value foo)")
$(warning origin=$(origin bar), flavor=$(flavor bar), value="$(value bar)")
ifdef foo
$(warning foo defined)
else
$(warning foo is not defined)
endif
ifdef $(bar)
$(warning bar defined)
else
$(warning bar is not defined)
endif
输出:
Makefile:3: origin=file, flavor=recursive, value="$(bar)"
Makefile:4: origin=file, flavor=recursive, value=""
Makefile:7: foo defined
Makefile:15: bar is not defined
然而,你可以强制扩展只需要一点点改变:在分配变量 foo 时添加冒号:foo:=$(bar),两者都不会被定义:
Makefile:3: origin=file, flavor=simple, value=""
Makefile:4: origin=file, flavor=recursive, value=""
Makefile:9: foo is not defined
Makefile:15: bar is not defined