Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/make/unit-tests make: add more tests for edge cases ...



details:   https://anonhg.NetBSD.org/src/rev/7059419b6f97
branches:  trunk
changeset: 959443:7059419b6f97
user:      rillig <rillig%NetBSD.org@localhost>
date:      Sun Feb 14 16:12:46 2021 +0000

description:
make: add more tests for edge cases in evaluating variable expressions

As a preparation for refactoring the code around variable expressions,
there need to be a few tests for indirect variable modifiers since these
were not covered before.

Indirect modifiers may include ':ts' and ':tW', which change the
interpretation of the variable expression in small details.  The scope
of these changes is limited to the indirect modifier, any evaluations
outside this indirect modifier are unaffected.

The changes to the .exp file are mostly line number changes, plus a
demonstration of a newly found bug, where an expression is evaluated
successfully despite producing a parse error.

diffstat:

 usr.bin/make/unit-tests/varmod-indirect.exp |  34 ++++++------
 usr.bin/make/unit-tests/varmod-indirect.mk  |  75 +++++++++++++++++++++++++++-
 2 files changed, 89 insertions(+), 20 deletions(-)

diffs (174 lines):

diff -r 2722e211bbe2 -r 7059419b6f97 usr.bin/make/unit-tests/varmod-indirect.exp
--- a/usr.bin/make/unit-tests/varmod-indirect.exp       Sun Feb 14 14:05:03 2021 +0000
+++ b/usr.bin/make/unit-tests/varmod-indirect.exp       Sun Feb 14 16:12:46 2021 +0000
@@ -1,18 +1,20 @@
-make: "varmod-indirect.mk" line 13: Unknown modifier '$'
-make: "varmod-indirect.mk" line 108: before
-make: "varmod-indirect.mk" line 108: after
-make: "varmod-indirect.mk" line 114: before
-make: "varmod-indirect.mk" line 114: after
-make: "varmod-indirect.mk" line 120: before
-make: "varmod-indirect.mk" line 120: after
-make: "varmod-indirect.mk" line 124: Unknown modifier 'Z'
-make: "varmod-indirect.mk" line 125: before
-make: "varmod-indirect.mk" line 125: after
-ParseReadLine (134): '_:=      before ${UNDEF} after'
+make: "varmod-indirect.mk" line 17: Unknown modifier '$'
+make: "varmod-indirect.mk" line 50: Unknown modifier '$'
+make: "varmod-indirect.mk" line 53: warning: FIXME: this expression should have resulted in a parse error rather than returning the unparsed portion of the expression.
+make: "varmod-indirect.mk" line 138: before
+make: "varmod-indirect.mk" line 138: after
+make: "varmod-indirect.mk" line 144: before
+make: "varmod-indirect.mk" line 144: after
+make: "varmod-indirect.mk" line 150: before
+make: "varmod-indirect.mk" line 150: after
+make: "varmod-indirect.mk" line 154: Unknown modifier 'Z'
+make: "varmod-indirect.mk" line 155: before
+make: "varmod-indirect.mk" line 155: after
+ParseReadLine (164): '_:=      before ${UNDEF} after'
 Global:_ = 
 Var_Parse: ${UNDEF} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Global:_ = before ${UNDEF} after
-ParseReadLine (137): '_:=      before ${UNDEF:${:US,a,a,}} after'
+ParseReadLine (167): '_:=      before ${UNDEF:${:US,a,a,}} after'
 Var_Parse: ${UNDEF:${:US,a,a,}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Var_Parse: ${:US,a,a,}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Applying ${:U...} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
@@ -27,7 +29,7 @@
 Applying ${:U...} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
 Result of ${:US,a,a,} is "S,a,a," (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_DEF)
 Global:_ = before ${UNDEF:S,a,a,} after
-ParseReadLine (147): '_:=      before ${UNDEF:${:U}} after'
+ParseReadLine (177): '_:=      before ${UNDEF:${:U}} after'
 Var_Parse: ${UNDEF:${:U}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Var_Parse: ${:U}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Applying ${:U} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
@@ -37,20 +39,20 @@
 Applying ${:U} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
 Result of ${:U} is "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_DEF)
 Global:_ = before ${UNDEF:} after
-ParseReadLine (152): '_:=      before ${UNDEF:${:UZ}} after'
+ParseReadLine (182): '_:=      before ${UNDEF:${:UZ}} after'
 Var_Parse: ${UNDEF:${:UZ}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Var_Parse: ${:UZ}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Applying ${:U...} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
 Result of ${:UZ} is "Z" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_DEF)
 Indirect modifier "Z" from "${:UZ}"
 Applying ${UNDEF:Z} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
-make: "varmod-indirect.mk" line 152: Unknown modifier 'Z'
+make: "varmod-indirect.mk" line 182: Unknown modifier 'Z'
 Result of ${UNDEF:Z} is error (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
 Var_Parse: ${:UZ}} after with VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF
 Applying ${:U...} to "" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_UNDEF)
 Result of ${:UZ} is "Z" (VARE_WANTRES|VARE_KEEP_DOLLAR|VARE_KEEP_UNDEF, none, VES_DEF)
 Global:_ = before ${UNDEF:Z} after
-ParseReadLine (154): '.MAKEFLAGS: -d0'
+ParseReadLine (184): '.MAKEFLAGS: -d0'
 ParseDoDependency(.MAKEFLAGS: -d0)
 Global:.MAKEFLAGS =  -r -k -d 0 -d pv -d
 Global:.MAKEFLAGS =  -r -k -d 0 -d pv -d 0
diff -r 2722e211bbe2 -r 7059419b6f97 usr.bin/make/unit-tests/varmod-indirect.mk
--- a/usr.bin/make/unit-tests/varmod-indirect.mk        Sun Feb 14 14:05:03 2021 +0000
+++ b/usr.bin/make/unit-tests/varmod-indirect.mk        Sun Feb 14 16:12:46 2021 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: varmod-indirect.mk,v 1.5 2020/12/27 17:32:25 rillig Exp $
+# $NetBSD: varmod-indirect.mk,v 1.6 2021/02/14 16:12:46 rillig Exp $
 #
 # Tests for indirect variable modifiers, such as in ${VAR:${M_modifiers}}.
 # These can be used for very basic purposes like converting a string to either
@@ -10,6 +10,10 @@
 
 # To apply a modifier indirectly via another variable, the whole
 # modifier must be put into a single variable expression.
+# The following expression generates a parse error since its indirect
+# modifier contains more than a sole variable expression.
+#
+# expect+1: Unknown modifier '$'
 .if ${value:L:${:US}${:U,value,replacement,}} != "S,value,replacement,}"
 .  warning unexpected
 .endif
@@ -28,13 +32,39 @@
 .endif
 
 
-# An indirect variable that evaluates to the empty string is allowed though.
+# An indirect variable that evaluates to the empty string is allowed.
+# It is even allowed to write another modifier directly afterwards.
+# There is no practical use case for this feature though, as demonstrated
+# in the test case directly below.
+.if ${value:L:${:Dempty}S,value,replaced,} != "replaced"
+.  warning unexpected
+.endif
+
+# If an expression for an indirect modifier evaluates to anything else than an
+# empty string and is neither followed by a ':' nor '}', this produces a parse
+# error.  Because of this parse error, this feature cannot be used reasonably
+# in practice.
+#
+# expect+1: Unknown modifier '$'
+#.MAKEFLAGS: -dvc
+.if ${value:L:${:UM*}S,value,replaced,} == "M*S,value,replaced,}"
+.  warning     FIXME: this expression should have resulted in a parse $\
+               error rather than returning the unparsed portion of the $\
+               expression.
+.else
+.  error
+.endif
+#.MAKEFLAGS: -d0
+
+# An indirect modifier can be followed by other modifiers, no matter if the
+# indirect modifier evaluates to an empty string or not.
+#
 # This makes it possible to define conditional modifiers, like this:
 #
 # M.little-endian=     S,1234,4321,
 # M.big-endian=                # none
-.if ${value:L:${:Dempty}S,a,A,} != "vAlue"
-.  warning unexpected
+.if ${value:L:${:D empty }:S,value,replaced,} != "replaced"
+.  error
 .endif
 
 
@@ -154,4 +184,41 @@
 .MAKEFLAGS: -d0
 .undef _
 
+
+# When evaluating indirect modifiers, these modifiers may expand to ':tW',
+# which modifies the interpretation of the expression value. This modified
+# interpretation only lasts until the end of the indirect modifier, it does
+# not influence the outer variable expression.
+.if ${1 2 3:L:tW:[#]} != 1             # direct :tW applies to the :[#]
+.  error
+.endif
+.if ${1 2 3:L:${:UtW}:[#]} != 3                # indirect :tW does not apply to :[#]
+.  error
+.endif
+
+
+# When evaluating indirect modifiers, these modifiers may expand to ':ts*',
+# which modifies the interpretation of the expression value. This modified
+# interpretation only lasts until the end of the indirect modifier, it does
+# not influence the outer variable expression.
+#
+# In this expression, the direct ':ts*' has no effect since ':U' does not
+# treat the expression value as a list of words but as a single word.  It has
+# to be ':U', not ':D', since the "expression name" is "1 2 3" and there is no
+# variable of that name.
+#.MAKEFLAGS: -dcpv
+.if ${1 2 3:L:ts*:Ua b c} != "a b c"
+.  error
+.endif
+# In this expression, the direct ':ts*' affects the ':M' at the end.
+.if ${1 2 3:L:ts*:Ua b c:M*} != "a*b*c"
+.  error
+.endif
+# In this expression, the ':ts*' is indirect, therefore the changed separator
+# only lasts until the end of the indirect modifier.  It does not affect the
+# ':M' since that is outside the scope.
+.if ${1 2 3:L:${:Uts*}:Ua b c:M*} != "a b c"
+.  error
+.endif
+
 all:



Home | Main Index | Thread Index | Old Index