Module Name:    src
Committed By:   rillig
Date:           Sat Oct 31 20:30:06 UTC 2020

Modified Files:
        src/usr.bin/make/unit-tests: Makefile varmod-gmtime.exp
            varmod-gmtime.mk varmod-localtime.exp varmod-localtime.mk

Log Message:
make(1): add more tests for the variable modifier :localtime


To generate a diff of this commit:
cvs rdiff -u -r1.179 -r1.180 src/usr.bin/make/unit-tests/Makefile
cvs rdiff -u -r1.4 -r1.5 src/usr.bin/make/unit-tests/varmod-gmtime.exp \
    src/usr.bin/make/unit-tests/varmod-localtime.mk
cvs rdiff -u -r1.5 -r1.6 src/usr.bin/make/unit-tests/varmod-gmtime.mk
cvs rdiff -u -r1.2 -r1.3 src/usr.bin/make/unit-tests/varmod-localtime.exp

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/unit-tests/Makefile
diff -u src/usr.bin/make/unit-tests/Makefile:1.179 src/usr.bin/make/unit-tests/Makefile:1.180
--- src/usr.bin/make/unit-tests/Makefile:1.179	Sat Oct 31 11:30:57 2020
+++ src/usr.bin/make/unit-tests/Makefile	Sat Oct 31 20:30:06 2020
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile,v 1.179 2020/10/31 11:30:57 rillig Exp $
+# $NetBSD: Makefile,v 1.180 2020/10/31 20:30:06 rillig Exp $
 #
 # Unit tests for make(1)
 #
@@ -378,6 +378,7 @@ ENV.envfirst=		FROM_ENV=value-from-env
 ENV.varmisc=		FROM_ENV=env
 ENV.varmisc+=		FROM_ENV_BEFORE=env
 ENV.varmisc+=		FROM_ENV_AFTER=env
+ENV.varmod-localtime+=	TZ=Europe/Berlin
 
 # Override make flags for some of the tests; default is -k.
 # If possible, write ".MAKEFLAGS: -dv" in the test .mk file instead of

Index: src/usr.bin/make/unit-tests/varmod-gmtime.exp
diff -u src/usr.bin/make/unit-tests/varmod-gmtime.exp:1.4 src/usr.bin/make/unit-tests/varmod-gmtime.exp:1.5
--- src/usr.bin/make/unit-tests/varmod-gmtime.exp:1.4	Sat Oct 31 19:55:26 2020
+++ src/usr.bin/make/unit-tests/varmod-gmtime.exp	Sat Oct 31 20:30:06 2020
@@ -2,7 +2,7 @@ mod-gmtime:
 %Y
 2020
 %Y
-%Y
+localtime == localtime
 mod-gmtime-indirect:
 make: Unknown modifier '1'
 
Index: src/usr.bin/make/unit-tests/varmod-localtime.mk
diff -u src/usr.bin/make/unit-tests/varmod-localtime.mk:1.4 src/usr.bin/make/unit-tests/varmod-localtime.mk:1.5
--- src/usr.bin/make/unit-tests/varmod-localtime.mk:1.4	Thu Oct 29 19:01:10 2020
+++ src/usr.bin/make/unit-tests/varmod-localtime.mk	Sat Oct 31 20:30:06 2020
@@ -1,7 +1,15 @@
-# $NetBSD: varmod-localtime.mk,v 1.4 2020/10/29 19:01:10 rillig Exp $
+# $NetBSD: varmod-localtime.mk,v 1.5 2020/10/31 20:30:06 rillig Exp $
 #
-# Tests for the :localtime variable modifier, which returns the given time,
-# formatted as a local timestamp.
+# Tests for the :localtime variable modifier, which formats a timestamp
+# using strftime(3) in local time.
+
+.if ${TZ} != "Europe/Berlin"	# see unit-tests/Makefile
+.  error
+.endif
+
+all:	mod-localtime
+all:	mod-localtime-indirect
+all:	parse-errors
 
 # Test for the default time format, %c.  Since the time always varies, it's
 # only possible to check for the general format here.  The names of the
@@ -11,7 +19,74 @@
 .  error
 .endif
 
-all:
-	@echo ${%Y:L:localtim=1593536400}	# modifier name too short
-	@echo ${%Y:L:localtime=1593536400}	# 2020-07-01T00:00:00Z
-	@echo ${%Y:L:localtimer=1593536400}	# modifier name too long
+mod-localtime:
+	@echo $@
+
+	# modifier name too short
+	@echo ${%Y:L:localtim=1593536400}
+
+	# 2020-07-01T00:00:00Z
+	@echo ${%Y:L:localtime=1593536400}
+
+	# modifier name too long
+	@echo ${%Y:L:localtimer=1593536400}
+
+	# If the modifier name is not matched exactly, fall back to the
+	# :from=to modifier.
+	@echo ${localtime:L:local%=gm%} == gmtime
+
+mod-localtime-indirect:
+	@echo $@:
+
+	# As of 2020-08-16, it is not possible to pass the seconds via a
+	# variable expression.  This is because parsing of the :localtime
+	# modifier stops at the '$' and returns to ApplyModifiers.
+	#
+	# There, a colon would be skipped but not a dollar.
+	# Parsing therefore continues at the '$' of the ${:U159...}, looking
+	# for an ordinary variable modifier.
+	#
+	# At this point, the ${:U} is expanded and interpreted as a variable
+	# modifier, which results in the error message "Unknown modifier '1'".
+	#
+	# If ApplyModifier_Localtime were to pass its argument through
+	# ParseModifierPart, this would work.
+	@echo ${%Y:L:localtime=${:U1593536400}}
+
+parse-errors:
+	@echo $@:
+
+	# As of 2020-10-31, it is possible to pass negative time stamps
+	# to the :localtime modifier, resulting in dates before 1970.
+	# Going back 50 years in the past is not a practical use case for
+	# make.
+	: -1 becomes ${:L:localtime=-1}.
+
+	# Spaces are allowed, not because it would make sense but just as
+	# a side-effect from using strtoul.
+	: space 1 becomes ${:L:localtime= 1}.
+
+	# 0 means now; to get consistent test results, the actual value has
+	# to be normalized.
+	: 0 becomes ${:L:localtime=0:C,^... ... .. ..:..:.. 20..$,ok,W}.
+
+	: 1 becomes ${:L:localtime=1}.
+
+	: INT32_MAX becomes ${:L:localtime=2147483647}.
+
+	# This may be different if time_t is still a 32-bit signed integer.
+	: INT32_MAX + 1 becomes ${:L:localtime=2147483648}.
+
+	# Integer overflow.
+	# Because this modifier is implemented using strtoul, the parsed
+	# time is ULONG_MAX, which gets converted to -1.  This results
+	# in a time stamp of the second before 1970 (in UTC) or 3599 seconds
+	# after New Year's Day in Europe/Berlin.
+	: overflow becomes ${:L:localtime=10000000000000000000000000000000}.
+
+	# As of 2020-10-31, there is no error handling while parsing the
+	# :localtime modifier, thus no error message is printed.  Parsing
+	# stops after the '=', and the remaining string is parsed for
+	# more variable modifiers.  Because of the unknown modifier 'e',
+	# the whole variable value is discarded and thus not printed.
+	: letter becomes ${:L:localtime=error}.

Index: src/usr.bin/make/unit-tests/varmod-gmtime.mk
diff -u src/usr.bin/make/unit-tests/varmod-gmtime.mk:1.5 src/usr.bin/make/unit-tests/varmod-gmtime.mk:1.6
--- src/usr.bin/make/unit-tests/varmod-gmtime.mk:1.5	Sat Oct 31 19:55:26 2020
+++ src/usr.bin/make/unit-tests/varmod-gmtime.mk	Sat Oct 31 20:30:06 2020
@@ -1,7 +1,7 @@
-# $NetBSD: varmod-gmtime.mk,v 1.5 2020/10/31 19:55:26 rillig Exp $
+# $NetBSD: varmod-gmtime.mk,v 1.6 2020/10/31 20:30:06 rillig Exp $
 #
 # Tests for the :gmtime variable modifier, which formats a timestamp
-# using strftime(3).
+# using strftime(3) in UTC.
 
 all:	mod-gmtime
 all:	mod-gmtime-indirect
@@ -17,10 +17,19 @@ all:	parse-errors
 
 mod-gmtime:
 	@echo $@:
-	@echo ${%Y:L:gmtim=1593536400}		# modifier name too short
-	@echo ${%Y:L:gmtime=1593536400}		# 2020-07-01T00:00:00Z
-	@echo ${%Y:L:gmtimer=1593536400}	# modifier name too long
-	@echo ${%Y:L:gm=gm:M*}
+
+	# modifier name too short
+	@echo ${%Y:L:gmtim=1593536400}
+
+	# 2020-07-01T00:00:00Z
+	@echo ${%Y:L:gmtime=1593536400}
+
+	# modifier name too long
+	@echo ${%Y:L:gmtimer=1593536400}
+
+	# If the modifier name is not matched exactly, fall back to the
+	# :from=to modifier.
+	@echo ${gmtime:L:gm%=local%} == localtime
 
 mod-gmtime-indirect:
 	@echo $@:
@@ -76,6 +85,3 @@ parse-errors:
 	# more variable modifiers.  Because of the unknown modifier 'e',
 	# the whole variable value is discarded and thus not printed.
 	: letter becomes ${:L:gmtime=error}.
-
-all:
-	@:;

Index: src/usr.bin/make/unit-tests/varmod-localtime.exp
diff -u src/usr.bin/make/unit-tests/varmod-localtime.exp:1.2 src/usr.bin/make/unit-tests/varmod-localtime.exp:1.3
--- src/usr.bin/make/unit-tests/varmod-localtime.exp:1.2	Sun Aug 23 15:13:21 2020
+++ src/usr.bin/make/unit-tests/varmod-localtime.exp	Sat Oct 31 20:30:06 2020
@@ -1,4 +1,19 @@
+mod-localtime
 %Y
 2020
 %Y
+gmtime == gmtime
+mod-localtime-indirect:
+make: Unknown modifier '1'
+
+parse-errors:
+: -1 becomes Thu Jan  1 00:59:59 1970.
+: space 1 becomes Thu Jan  1 01:00:01 1970.
+: 0 becomes ok.
+: 1 becomes Thu Jan  1 01:00:01 1970.
+: INT32_MAX becomes Tue Jan 19 04:14:07 2038.
+: INT32_MAX + 1 becomes Tue Jan 19 04:14:08 2038.
+: overflow becomes Thu Jan  1 00:59:59 1970.
+make: Unknown modifier 'e'
+: letter becomes .
 exit status 0

Reply via email to