是否可以安全地"展开makefile中的变量,转义makefile认为特殊的所有字符?
例如,假设变量用作目标:
${external_chaos}:
dd if=/dev/zero of=${external_chaos}
(故意示例中的戏剧)
如果external_chaos
包含空格,;
,#
,:
,,
或其他具有重要文件字符的字符,那么整个规则就会搞砸
我认为作为解决方案的是一些Make内置函数应该这样做,例如${escape external_chaos}
(想象中的奢侈品)。
${value external_chaos}
没有做到。
答案 0 :(得分:3)
一般来说,在使用带有空格的目标时,你不会成功(没有大的痛苦,如果有的话)。放弃吧。如果你必须支持带有空格的目标,那么选择一个不同的构建工具,而不是make。
简短的回答是否定的,没有内置功能。你可以使用subst
自己写一个;例如,在目标中,您需要至少转义%
和:
:
TESCAPE = $(subst :,\:,$(subst %,\%,$1))
另一方面,请注意;
和,
在目标中并不特殊,因此您根本不需要逃避它们;事实上,如果你这样做会得到不正确的结果,因为\
将保留在目标名称中:反斜杠只有在引用特殊字符时才会被删除。
#
在定义变量时很特别,但是当变量展开时却不是这样:解析器已经完成了查找注释。所以你必须写:
external_chaos = foo\#bar,biz;baz:boz%bin
首先将#
放入变量中,但是在使用变量时,您不需要在使用该变量时将其转义。
下一个有趣的事情是你需要以不同的方式逃避目标和先决条件。例如,在目标中,您必须不转义;
,但在先决条件中,必须转义;
。所以你需要不同的宏:
PESCAPE = $(subst :,\:,$(subst ;,\;,$1))
TESCAPE = $(subst :,\:,$(subst %,\%,$1))
all: $(call PESCAPE,${external_chaos})
$(call TESCAPE,${external_chaos}): ; echo '$@'
给出:
foo#bar,biz;baz:boz%bin