xref: /freebsd/contrib/bmake/unit-tests/varmod-loop-delete.mk (revision 6a7405f5a6b639682cacf01e35d561411ff556aa)
1*6a7405f5SSimon J. Gerraty# $NetBSD: varmod-loop-delete.mk,v 1.7 2024/08/29 20:20:36 rillig Exp $
212904384SSimon J. Gerraty#
312904384SSimon J. Gerraty# Tests for the variable modifier ':@', which as a side effect allows to
412904384SSimon J. Gerraty# delete an arbitrary variable.
512904384SSimon J. Gerraty
612904384SSimon J. Gerraty# A side effect of the modifier ':@' is that the loop variable is created as
712904384SSimon J. Gerraty# an actual variable in the current evaluation scope (Command/Global/target),
812904384SSimon J. Gerraty# and at the end of the loop, this variable is deleted.  Since var.c 1.204
912904384SSimon J. Gerraty# from 2016-02-18 and before var.c 1.963 from 2021-12-05, a variable could be
1012904384SSimon J. Gerraty# deleted while it was in use, leading to a use-after-free bug.
1112904384SSimon J. Gerraty#
1212904384SSimon J. Gerraty# See Var_Parse, comment 'the value of the variable must not change'.
1312904384SSimon J. Gerraty
1412904384SSimon J. Gerraty# Set up the variable that deletes itself when it is evaluated.
1512904384SSimon J. GerratyVAR=	${:U:@VAR@@} rest of the value
1612904384SSimon J. Gerraty
1712904384SSimon J. Gerraty# In an assignment, the scope is 'Global'.  Since the variable 'VAR' is
1812904384SSimon J. Gerraty# defined in the global scope, it deletes itself.
19*6a7405f5SSimon J. Gerraty# expect+1: Cannot delete variable "VAR" while it is used
2012904384SSimon J. GerratyEVAL:=	${VAR}
2112904384SSimon J. Gerraty.if ${EVAL} != " rest of the value"
2212904384SSimon J. Gerraty.  error
2312904384SSimon J. Gerraty.endif
2412904384SSimon J. Gerraty
2512904384SSimon J. GerratyVAR=	${:U:@VAR@@} rest of the value
2612904384SSimon J. Gerratyall: .PHONY
2712904384SSimon J. Gerraty	# In the command that is associated with a target, the scope is the
2812904384SSimon J. Gerraty	# one from the target.  That scope only contains a few variables like
2912904384SSimon J. Gerraty	# '.TARGET', '.ALLSRC', '.IMPSRC'.  Make does not expect that these
3012904384SSimon J. Gerraty	# variables get modified from the outside.
3112904384SSimon J. Gerraty	#
3212904384SSimon J. Gerraty	# There is no variable named 'VAR' in the local scope, so nothing
3312904384SSimon J. Gerraty	# happens.
3412904384SSimon J. Gerraty	: $@: '${VAR}'
35