make: fix wrong expression evaluation in -dL mode

The modifier ':C' now only compiles the regular expression if the result
of the expression is actually needed.

Several other modifiers have the same bug of evaluating the expression
in cases where this is not needed.  It just doesn't show up because they
don't have any noticeable side effects, other than wasting CPU time.
This affects irrelevant conditions as well.
This commit is contained in:
rillig 2021-03-14 10:57:12 +00:00
parent 0ed436993c
commit 8902b05acf
3 changed files with 18 additions and 10 deletions

View File

@ -3,7 +3,6 @@ make: "opt-debug-lint.mk" line 41: Variable "UNDEF" is undefined
make: "opt-debug-lint.mk" line 61: Missing delimiter ':' after modifier "L"
make: "opt-debug-lint.mk" line 61: Missing delimiter ':' after modifier "P"
make: "opt-debug-lint.mk" line 69: Unknown modifier "${"
make: Regex compilation error: (details omitted)
make: Fatal errors encountered -- cannot continue
make: stopped in unit-tests
exit status 1

View File

@ -1,4 +1,4 @@
# $NetBSD: opt-debug-lint.mk,v 1.13 2021/03/14 10:45:51 rillig Exp $
# $NetBSD: opt-debug-lint.mk,v 1.14 2021/03/14 10:57:12 rillig Exp $
#
# Tests for the -dL command line option, which runs additional checks
# to catch common mistakes, such as unclosed variable expressions.
@ -77,12 +77,15 @@ ${UNDEF}: ${UNDEF}
. error
.endif
# Before var.c 1.XXX from 2021-03-14, the whole variable text was evaluated
# to check for unclosed expressions and unknown operators. During this check,
# the subexpression '${:U2}' was not expanded, instead it was copied verbatim
# into the regular expression, which was '.*=.{1,${:U2}}$'. This regular
# expression was then compiled (despite VARE_WANTRES being unset), which
# resulted in a wrong error message.
# In lint mode, the whole variable text is evaluated to check for unclosed
# expressions and unknown operators. During this check, the subexpression
# '${:U2}' is not expanded, instead it is copied verbatim into the regular
# expression, leading to '.*=.{1,${:U2}}$'.
#
# Before var.c 1.856 from 2021-03-14, this regular expression was then
# compiled even though that was not necessary for checking the syntax at the
# level of variable expressions. The unexpanded '$' then resulted in a wrong
# error message.
#
# This only happened in lint mode since in default mode the early check for
# unclosed expressions and unknown modifiers is skipped.

View File

@ -1,4 +1,4 @@
/* $NetBSD: var.c,v 1.855 2021/02/23 16:29:52 rillig Exp $ */
/* $NetBSD: var.c,v 1.856 2021/03/14 10:57:12 rillig Exp $ */
/*
* Copyright (c) 1988, 1989, 1990, 1993
@ -140,7 +140,7 @@
#include "metachar.h"
/* "@(#)var.c 8.3 (Berkeley) 3/19/94" */
MAKE_RCSID("$NetBSD: var.c,v 1.855 2021/02/23 16:29:52 rillig Exp $");
MAKE_RCSID("$NetBSD: var.c,v 1.856 2021/03/14 10:57:12 rillig Exp $");
typedef enum VarFlags {
VFL_NONE = 0,
@ -2892,6 +2892,12 @@ ApplyModifier_Regex(const char **pp, ApplyModifiersState *st)
break;
}
if (!(st->expr->eflags & VARE_WANTRES)) {
free(args.replace);
free(re);
return AMR_OK;
}
error = regcomp(&args.re, re, REG_EXTENDED);
free(re);
if (error != 0) {