Module Name: src Committed By: rillig Date: Mon Nov 2 22:44:29 UTC 2020
Modified Files: src/usr.bin/make: parse.c src/usr.bin/make/unit-tests: varname.exp varname.mk Log Message: make(1): document undefined behavior in Parse_IsVar Sigh. If only C could be compiled in strict mode that detects these out-of-bounds memory accesses. To generate a diff of this commit: cvs rdiff -u -r1.420 -r1.421 src/usr.bin/make/parse.c cvs rdiff -u -r1.5 -r1.6 src/usr.bin/make/unit-tests/varname.exp cvs rdiff -u -r1.6 -r1.7 src/usr.bin/make/unit-tests/varname.mk Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/usr.bin/make/parse.c diff -u src/usr.bin/make/parse.c:1.420 src/usr.bin/make/parse.c:1.421 --- src/usr.bin/make/parse.c:1.420 Sun Nov 1 00:24:57 2020 +++ src/usr.bin/make/parse.c Mon Nov 2 22:44:29 2020 @@ -1,4 +1,4 @@ -/* $NetBSD: parse.c,v 1.420 2020/11/01 00:24:57 rillig Exp $ */ +/* $NetBSD: parse.c,v 1.421 2020/11/02 22:44:29 rillig Exp $ */ /* * Copyright (c) 1988, 1989, 1990, 1993 @@ -117,7 +117,7 @@ #include "pathnames.h" /* "@(#)parse.c 8.3 (Berkeley) 3/19/94" */ -MAKE_RCSID("$NetBSD: parse.c,v 1.420 2020/11/01 00:24:57 rillig Exp $"); +MAKE_RCSID("$NetBSD: parse.c,v 1.421 2020/11/02 22:44:29 rillig Exp $"); /* types and constants */ @@ -1850,6 +1850,8 @@ Parse_IsVar(const char *p, VarAssign *ou #endif /* Scan for one of the assignment operators outside a variable expansion */ + /* FIXME: undefined behavior. In unit-tests/varname.mk:try1, at the end + * of the loop, p already points to the next line. */ while ((ch = *p++) != 0) { if (ch == '(' || ch == '{') { level++; Index: src/usr.bin/make/unit-tests/varname.exp diff -u src/usr.bin/make/unit-tests/varname.exp:1.5 src/usr.bin/make/unit-tests/varname.exp:1.6 --- src/usr.bin/make/unit-tests/varname.exp:1.5 Mon Nov 2 22:29:48 2020 +++ src/usr.bin/make/unit-tests/varname.exp Mon Nov 2 22:44:29 2020 @@ -9,16 +9,16 @@ Applying ${:U...} to "" (VARE_UNDEFERR|V Result of ${:UVAR(((} is "VAR(((" (VARE_UNDEFERR|VARE_WANTRES, none, VEF_UNDEF|VEF_DEF) Global:.ALLTARGETS = VAR(((=) No closing parenthesis in archive specification -make: "varname.mk" line 26: Error in archive specification: "VAR" +make: "varname.mk" line 29: Error in archive specification: "VAR" Var_Parse: ${:UVAR\(\(\(}= try2 with VARE_UNDEFERR|VARE_WANTRES Applying ${:U...} to "" (VARE_UNDEFERR|VARE_WANTRES, none, VEF_UNDEF) Result of ${:UVAR\(\(\(} is "VAR\(\(\(" (VARE_UNDEFERR|VARE_WANTRES, none, VEF_UNDEF|VEF_DEF) Global:.ALLTARGETS = VAR(((=) VAR\(\(\(= -make: "varname.mk" line 27: Need an operator +make: "varname.mk" line 30: Need an operator Var_Parse: ${:UVAR\(\(\(}= try3 with VARE_UNDEFERR|VARE_WANTRES Applying ${:U...} to "" (VARE_UNDEFERR|VARE_WANTRES, none, VEF_UNDEF) Result of ${:UVAR\(\(\(} is "VAR\(\(\(" (VARE_UNDEFERR|VARE_WANTRES, none, VEF_UNDEF|VEF_DEF) -make: "varname.mk" line 28: Need an operator +make: "varname.mk" line 31: Need an operator Global:.MAKEFLAGS = -r -k -d v -d Global:.MAKEFLAGS = -r -k -d v -d 0 make: Fatal errors encountered -- cannot continue Index: src/usr.bin/make/unit-tests/varname.mk diff -u src/usr.bin/make/unit-tests/varname.mk:1.6 src/usr.bin/make/unit-tests/varname.mk:1.7 --- src/usr.bin/make/unit-tests/varname.mk:1.6 Mon Nov 2 22:29:48 2020 +++ src/usr.bin/make/unit-tests/varname.mk Mon Nov 2 22:44:29 2020 @@ -1,4 +1,4 @@ -# $NetBSD: varname.mk,v 1.6 2020/11/02 22:29:48 rillig Exp $ +# $NetBSD: varname.mk,v 1.7 2020/11/02 22:44:29 rillig Exp $ # # Tests for special variables, such as .MAKE or .PARSEDIR. # And for variable names in general. @@ -23,6 +23,10 @@ ${VARNAME}= 3 open parentheses # In the above test, the variable name is constructed indirectly. Neither # of the following expressions produces the intended effect. +# +# This is not a variable assignment since the parentheses and braces are not +# balanced. At the end of the line, there are still 3 levels open, which +# means the variable name is not finished. ${:UVAR(((}= try1 ${:UVAR\(\(\(}= try2 ${:UVAR\(\(\(}= try3