mirror of
https://git.FreeBSD.org/src.git
synced 2024-12-01 08:27:59 +00:00
ee914ef902
Lots more unit tests and code cleanup Relevant changes from ChangeLog o job.c: Print -de error information when running multiple jobs o var.c: only report error for unmatched regex subexpression when linting (-dL) since we cannot tell when an unmatched subexpression is an expected result. reduce memory allocations in the modifiers ':D' and ':U' reduce memory allocation and strlen calls in modifier ':from=to' in the ':Q' modifier, only allocate memory if necessary improve performance for LazyBuf reduce debug logging and memory allocation for ${:U...} reduce verbosity of the -dv debug logging for standard cases fix double varname expansion in the variable modifier '::=' o var.c: avoid evaluating many modifiers in parse only mode in strict mode (-dL) many variable references are parsed twice, the first time just to report parse errors early, so we want to avoid side effects and wasted effort to the extent possible.
70 lines
2.6 KiB
Makefile
Executable File
70 lines
2.6 KiB
Makefile
Executable File
# $NetBSD: varname-empty.mk,v 1.9 2021/04/04 10:13:09 rillig Exp $
|
|
#
|
|
# Tests for the special variable with the empty name.
|
|
#
|
|
# There is no variable named "" at all, and this fact is used a lot in
|
|
# variable expressions of the form ${:Ufallback}. These expressions are
|
|
# based on the variable named "" and use the :U modifier to assign a
|
|
# fallback value to the expression (but not to the variable).
|
|
#
|
|
# This form of expressions is used to implement value substitution in the
|
|
# .for loops. Another use case is in a variable assignment of the form
|
|
# ${:Uvarname}=value, which allows for characters in the variable name that
|
|
# would otherwise be interpreted by the parser, such as whitespace, ':',
|
|
# '=', '$', backslash.
|
|
#
|
|
# The only places where a variable is assigned a value are Var_Set and
|
|
# Var_Append, and these places protect the variable named "" from being
|
|
# defined. This is different from read-only variables, as that flag can
|
|
# only apply to variables that are defined. The variable named "" must
|
|
# never be defined though.
|
|
#
|
|
# See also:
|
|
# The special variables @F or ^D, in var-class-local.mk
|
|
|
|
# Until 2020-08-22 it was possible to assign a value to the variable with
|
|
# the empty name, leading to all kinds of unexpected effects in .for loops
|
|
# and other places that assume that ${:Ufallback} expands to "fallback".
|
|
# The bug in Var_Set was that only expanded variables had been checked for
|
|
# the empty name, but not the direct assignments with an empty name.
|
|
?= default
|
|
= assigned # undefined behavior until 2020-08-22
|
|
+= appended
|
|
:= subst
|
|
!= echo 'shell-output'
|
|
.if ${:Ufallback} != "fallback"
|
|
. error
|
|
.endif
|
|
|
|
${:U}= assigned indirectly
|
|
.if ${:Ufallback} != "fallback"
|
|
. error
|
|
.endif
|
|
|
|
${:U}+= appended indirectly
|
|
.if ${:Ufallback} != "fallback"
|
|
. error
|
|
.endif
|
|
|
|
.MAKEFLAGS: -d0
|
|
|
|
# Before 2020-08-22, the simple assignment operator '=' after an empty
|
|
# variable name had an off-by-one bug in Parse_Var. The code that was
|
|
# supposed to "skip to operator character" started its search _after_ the
|
|
# assignment operator, assuming that the variable name would be at least
|
|
# one character long. It then looked for the next occurrence of a '=', which
|
|
# could be several lines away or not occur at all. While looking for the
|
|
# '=', some whitespace was nulled out, leading to out-of-bounds write.
|
|
= assigned # undefined behavior until 2020-08-22
|
|
|
|
# The .for loop expands the expression ${i} to ${:U1}, ${:U2} and so on.
|
|
# This only works if the variable with the empty name is guaranteed to
|
|
# be undefined.
|
|
.for i in 1 2 3
|
|
NUMBERS+= ${i}
|
|
.endfor
|
|
|
|
all:
|
|
@echo out: ${:Ufallback}
|
|
@echo out: ${NUMBERS}
|