Skip to content

Commit

Permalink
Squashed 'tz/' changes from 6903dde39e..5ad5cfba5b
Browse files Browse the repository at this point in the history
a8e2fcd87b Release 2025a
4ab8692704 Fix bugs in -Wcast-qual pacification
1ee9daa918 Pacify gcc -Wcast-qual
e8920e76fc Rename emalloc to xmalloc.
cda7ec0702 Alias asctime, ctime result
edbabecc14 Fix ctime conformace bug
7db03d5b98 Add missing zdump.o dependency
e8e1a3d25b NetBSD defines STD_INSPIRED functions
d89a7468e3 newctime doc improvements
da932ff7ec Stop using \*- in man pages
b6adb83ce3 Warn about 2-digit years in strftime man page
562a1f1631 Modernize date man page
9ab3f52d34 No leap second on 2025-06-30
e5aaf1c7fe For timestamps compare to HEAD not to index
aa8a059d13 State the duplicate guideline more clearly
cb537f2001 Suggest -Dssize_t=int, not long
352dcdf9e3 Port S_ISREG to ancient UNIX, recent MS-Windows
3411494cc7 Define _CRT_DECLARE_NONSTDC_NAMES for MS-Windows
7d776e798c Port ‘utc’ to MS-Windows
7c90916644 Define NOMINMAX for MS-Windows
94931e3006 Fix asctime.o, strftime.o dependencies
d23b9bf5fd Fix to2050.tzs timestamp in distributed tarball
24a4d97fc0 'zdump -' now reads from stdin
6d77c92872 Bring back zdump on a pipe
f5d6c1d7d9 Invalid TZ now abbreviates as "-00" not "UTC"
a7ad244f30 Check for TZ naming a device
43cc9b6149 Fix unlikely multithreaded file descriptor leak
b208d5841e Etc/Unknown is now reserved
13bc796952 Update USDOT map description
de6dab1b23 Fix checknow confusing diagnostics
5e95797d9a * tz-link.html: Mention DoT geodata (thanks to Roozbeh Pournader).
3862447e2d Optimize asctime snprintf calls
161563657b Port recent asctime snprintf changes to NetBSD
e6d6bc3e45 Pacify gcc -Wsuggest-attribute=format sans snprintf in zdump
9955786265 TZNAME_MAXIMUM defaults to 254, not 255
fe5be99d8d Be more consistent about macro true/false vs 1/0
3d5e7acb88 Port asctime_r to POSIX.1-2017 and earlier
31f483a149 Remove dependency of asctime on strftime
7ef7ed06b2 Simplify timeoff redefinition
1bd67a4b75 Move MKTIME_MIGHT_OVERFLOW definition
67f7e8ab9c Pacify GCC 15ish -Wzero-as-null-pointer-constant
535a4e8b25 Pacify GCC 15ish -Wleading-whitespace=blanks
59ae22db9b Revert zone.tab changes for Concordia, EBO
abb83041a2 Fix mktime/timeoff overflow bug
0706ef0bf8 Move iinntt definition
fa004d323c Add two research stations to zone*.tab
38eea0e263 Reorder australia comments
77820eb701 Mention the Eyre Bird Observatory
d9e7a42f11 Avoid time_t + int overflow
ea814e998d strftime %s no longer is limited to time_t range
b2ee68e092 Simplify AmigaOS support
41e5344e6f Fix bug near the year 2**31 - 1 - 1900
4e1de2496e Pacify gcc -Wsuggest-attribute=const
ebd2ed9235 Don’t define _FILE_OFFSET_BITS if _TIME_BITS
26a649a19e Improve zdump overflow checking
81bab74a7f * northamerica: Also mention Sandford Fleming and Cleveland Abbe.
cfacf5ea70 strftime now outputs unknown conversions as-is
9c8221d79c * private.h: Fix timeoff comment.
705dc023c2 Remove now-dead strftime code
d8b6fe65c9 Fix Asia/Manila post-1990 typo
3a83f10003 * NEWS, europe: Belated thanks for Ittoqqortoormiit 2024 fix
17fbd40e5c * NEWS: Belated thanks for Palestine 2072-2075 fix
493df554af Prefer www.rfc-editor.org for RFCs
9db906a00f Switch from RFC 8536 to 9636 for documentation
be62d59182 Talk a bit more about tm_isdst's obsolescence
258a3775c0 tzfile man page editorial changes
af54a9e896 Port better to glibc when used internally there
486e1e890e Paraguay tm_isdst flag goes to 0 today
636e6f983b Paraguay adopts permanent -03 starting spring 2024
e6258faabc Concordia can use Asia/Singapore
19b35d7db2 More changes for global-tz convenience
07731a9f6a "j" could mean June, too
66183d1e25 Fix "many" typo in NEWS
96fa7b7dd4 Document month, weekday names better
7b6fb155ca Improve style checks for months
926b507fa5 "Apr", not "April", in IN column
d4c65d53b9 Improve historical data for the Philippines

git-subtree-dir: tz
git-subtree-split: 5ad5cfba5b092fe6abdc6870438cc09bcffbdd4b
  • Loading branch information
stub42 committed Jan 31, 2025
1 parent 382ca0c commit 7abdc14
Show file tree
Hide file tree
Showing 34 changed files with 1,288 additions and 883 deletions.
32 changes: 17 additions & 15 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@ TIME_T_ALTERNATIVES_TAIL = int_least32_t.ck uint_least32_t.ck \
uint_least64_t.ck

# What kind of TZif data files to generate. (TZif is the binary time
# zone data format that zic generates; see Internet RFC 8536.)
# zone data format that zic generates; see Internet RFC 9636.)
# If you want only POSIX time, with time values interpreted as
# seconds since the epoch (not counting leap seconds), use
# REDO= posix_only
Expand Down Expand Up @@ -255,14 +255,15 @@ LDLIBS=
# -DHAVE_UNISTD_H=0 if <unistd.h> does not work*
# -DHAVE_UTMPX_H=0 if <utmpx.h> does not work*
# -Dlocale_t=XXX if your system uses XXX instead of locale_t
# -DMKTIME_MIGHT_OVERFLOW if mktime might fail due to time_t overflow
# -DPORT_TO_C89 if tzcode should also run on mostly-C89 platforms+
# Typically it is better to use a later standard. For example,
# with GCC 4.9.4 (2016), prefer '-std=gnu11' to '-DPORT_TO_C89'.
# Even with -DPORT_TO_C89, the code needs at least one C99
# feature (integers at least 64 bits wide) and maybe more.
# -DRESERVE_STD_EXT_IDS if your platform reserves standard identifiers
# with external linkage, e.g., applications cannot define 'localtime'.
# -Dssize_t=long on hosts like MS-Windows that lack ssize_t
# -Dssize_t=int on hosts like MS-Windows that lack ssize_t
# -DSUPPORT_C89=0 if the tzcode library should not support C89 callers
# Although -DSUPPORT_C89=0 might work around latent bugs in callers,
# it does not conform to POSIX.
Expand All @@ -285,7 +286,7 @@ LDLIBS=
# This mishandles some past timestamps, as US DST rules have changed.
# It also mishandles settings like TZ='EET-2EEST' for eastern Europe,
# as Europe and US DST rules differ.
# -DTZNAME_MAXIMUM=N to limit time zone abbreviations to N bytes (default 255)
# -DTZNAME_MAXIMUM=N to limit time zone abbreviations to N bytes (default 254)
# -DUNINIT_TRAP if reading uninitialized storage can cause problems
# other than simply getting garbage data
# -DUSE_LTZ=0 to build zdump with the system time zone library
Expand Down Expand Up @@ -319,7 +320,8 @@ GCC_DEBUG_FLAGS = -DGCC_LINT -g3 -O3 \
$(GCC_INSTRUMENT) \
-Wall -Wextra \
-Walloc-size-larger-than=100000 -Warray-bounds=2 \
-Wbad-function-cast -Wbidi-chars=any,ucn -Wcast-align=strict -Wdate-time \
-Wbad-function-cast -Wbidi-chars=any,ucn -Wcast-align=strict -Wcast-qual \
-Wdate-time \
-Wdeclaration-after-statement -Wdouble-promotion \
-Wduplicated-branches -Wduplicated-cond -Wflex-array-member-not-at-end \
-Wformat=2 -Wformat-overflow=2 -Wformat-signedness -Wformat-truncation \
Expand All @@ -336,7 +338,7 @@ GCC_DEBUG_FLAGS = -DGCC_LINT -g3 -O3 \
-Wsuggest-attribute=noreturn -Wsuggest-attribute=pure \
-Wtrampolines -Wundef -Wunused-macros -Wuse-after-free=3 \
-Wvariadic-macros -Wvla -Wwrite-strings \
-Wno-format-nonliteral -Wno-sign-compare
-Wno-format-nonliteral -Wno-sign-compare -Wno-type-limits
#
# If your system has a "GMT offset" field in its "struct tm"s
# (or if you decide to add such a field in your system's "time.h" file),
Expand Down Expand Up @@ -614,8 +616,8 @@ TZS_YEAR= 2050
TZS_CUTOFF_FLAG= -c $(TZS_YEAR)
TZS= to$(TZS_YEAR).tzs
TZS_NEW= to$(TZS_YEAR)new.tzs
TZS_DEPS= $(YDATA) asctime.c localtime.c \
private.h tzfile.h zdump.c zic.c
TZS_DEPS= $(YDATA) localtime.c private.h \
strftime.c tzfile.h zdump.c zic.c
TZDATA_DIST = $(COMMON) $(DATA) $(MISC)
# EIGHT_YARDS is just a yard short of the whole ENCHILADA.
EIGHT_YARDS = $(TZDATA_DIST) $(DOCS) $(SOURCES) tzdata.zi
Expand Down Expand Up @@ -855,10 +857,10 @@ tzselect: tzselect.ksh version
chmod +x $@.out
mv $@.out $@
check: check_mild back.ck
check: check_mild back.ck now.ck
check_mild: check_web check_zishrink \
character-set.ck white-space.ck links.ck mainguard.ck \
name-lengths.ck now.ck slashed-abbrs.ck sorted.ck \
name-lengths.ck slashed-abbrs.ck sorted.ck \
tables.ck ziguard.ck tzs.ck
# True if UTF8_LOCALE does not work;
Expand Down Expand Up @@ -1103,7 +1105,7 @@ set-timestamps.out: $(EIGHT_YARDS)
touch -md @1 test.out; then \
rm -f test.out && \
for file in $$files; do \
if git diff --quiet $$file; then \
if git diff --quiet HEAD $$file; then \
time=$$(TZ=UTC0 git log -1 \
--format='tformat:%cd' \
--date='format:%Y-%m-%dT%H:%M:%SZ' \
Expand Down Expand Up @@ -1354,13 +1356,13 @@ long-long.ck unsigned.ck: $(VERSION_DEPS)
zonenames: tzdata.zi
@$(AWK) '/^Z/ { print $$2 } /^L/ { print $$3 }' tzdata.zi
asctime.o: private.h tzfile.h
asctime.o: private.h
date.o: private.h
difftime.o: private.h
localtime.o: private.h tzfile.h tzdir.h
strftime.o: private.h tzfile.h
zdump.o: version.h
zic.o: private.h tzfile.h tzdir.h version.h
localtime.o: private.h tzdir.h tzfile.h
strftime.o: localtime.c private.h tzdir.h tzfile.h
zdump.o: private.h version.h
zic.o: private.h tzdir.h tzfile.h version.h
.PHONY: ALL INSTALL all
.PHONY: check check_mild check_time_t_alternatives
Expand Down
84 changes: 81 additions & 3 deletions NEWS
Original file line number Diff line number Diff line change
@@ -1,5 +1,83 @@
News for the tz database

Release 2025a - 2025-01-15 10:47:24 -0800

Briefly:
Paraguay adopts permanent -03 starting spring 2024.
Improve pre-1991 data for the Philippines.
Etc/Unknown is now reserved.

Changes to future timestamps

Paraguay will stop changing its clocks after the spring-forward
transition on 2024-10-06, so it is now permanently at -03.
(Thanks to Heitor David Pinto and Even Scharning.)
This affects timestamps starting 2025-03-22, as well as the
obsolescent tm_isdst flags starting 2024-10-15.

Changes to past timestamps

Correct timestamps for the Philippines before 1900, and from 1937
through 1990. (Thanks to P Chan for the heads-up and citations.)
This includes adjusting local mean time before 1899; fixing
transitions in September 1899, January 1937, and June 1954; adding
transitions in December 1941, November 1945, March and September
1977, and May and July 1990; and removing incorrect transitions in
March and September 1978.

Changes to data

Add zone1970.tab lines for the Concordia and Eyre Bird Observatory
research stations. (Thanks to Derick Rethans and Jule Dabars.)

Changes to code

strftime %s now generates the correct numeric string even when the
represented number does not fit into time_t. This is better than
generating the numeric equivalent of (time_t) -1, as strftime did
in TZDB releases 96a (when %s was introduced) through 2020a and in
releases 2022b through 2024b. It is also better than failing and
returning 0, as strftime did in releases 2020b through 2022a.

strftime now outputs an invalid conversion specifier as-is,
instead of eliding the leading '%', which confused debugging.

An invalid TZ now generates the time zone abbreviation "-00", not
"UTC", to help the user see that an error has occurred. (Thanks
to Arthur David Olson for suggesting a "wrong result".)

mktime and timeoff no longer incorrectly fail merely because a
struct tm component near INT_MIN or INT_MAX overflows when a
lower-order component carries into it.

TZNAME_MAXIMUM, the maximum number of bytes in a proleptic TZ
string's time zone abbreviation, now defaults to 254 not 255.
This helps reduce the size of internal state from 25480 to 21384
on common platforms. This change should not be a problem, as
nobody uses such long "abbreviations" and the longstanding tzcode
maximum was 16 until release 2023a. For those who prefer no
arbitrary limits, you can now specify TZNAME_MAXIMUM values up to
PTRDIFF_MAX, a limit forced by C anyway; formerly tzcode silently
misbehaved unless TZNAME_MAXIMUM was less than INT_MAX.

tzset and related functions no longer leak a file descriptor if
another thread forks or execs at about the same time and if the
platform has O_CLOFORK and O_CLOEXEC respectively. Also, the
functions no longer let a TZif file become a controlling terminal.

'zdump -' now reads TZif data from /dev/stdin.
(From a question by Arthur David Olson.)

Changes to documentation

The name Etc/Unknown is now reserved: it will not be used by TZDB.
This is for compatibility with CLDR, which uses the string
"Etc/Unknown" for an unknown or invalid timezone. (Thanks to
Justin Grant, Mark Davis, and Guy Harris.)

Cite Internet RFC 9636, which obsoletes RFC 8536 for TZif format.


Release 2024b - 2024-09-04 12:27:47 -0700

Briefly:
Expand Down Expand Up @@ -116,7 +194,7 @@ Release 2024b - 2024-09-04 12:27:47 -0700
Changes to commentary

Commentary about historical transitions in Portugal and her former
colonies has been expanded with links to many relevant legislation.
colonies has been expanded with links to relevant legislation.
(Thanks to Tim Parenti.)


Expand Down Expand Up @@ -204,10 +282,10 @@ Release 2023d - 2023-12-21 20:02:24 -0800
changing its time zone from -01/+00 to -02/-01 at the same moment
as the spring-forward transition. Its clocks will therefore not
spring forward as previously scheduled. The time zone change
reverts to its common practice before 1981.
reverts to its common practice before 1981. (Thanks to Jule Dabars.)

Fix predictions for DST transitions in Palestine in 2072-2075,
correcting a typo introduced in 2023a.
correcting a typo introduced in 2023a. (Thanks to Jule Dabars.)

Changes to past and future timestamps

Expand Down
2 changes: 2 additions & 0 deletions antarctica
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,8 @@ Zone Antarctica/Mawson 0 - -00 1954 Feb 13

# France & Italy - year-round base
# Concordia, -750600+1232000, since 2005
# https://en.wikipedia.org/wiki/Concordia_Station
# Can use Asia/Singapore, which it has agreed with since inception.

# Germany - year-round base
# Neumayer III, -704080-0081602, since 2009
Expand Down
118 changes: 66 additions & 52 deletions asctime.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

/*
** Avoid the temptation to punt entirely to strftime;
** strftime can behave badly when tm components are out of range, and
** the output of strftime is supposed to be locale specific
** whereas the output of asctime is supposed to be constant.
*/
Expand All @@ -16,27 +17,6 @@
#include "private.h"
#include <stdio.h>

/*
** All years associated with 32-bit time_t values are exactly four digits long;
** some years associated with 64-bit time_t values are not.
** Vintage programs are coded for years that are always four digits long
** and may assume that the newline always lands in the same place.
** For years that are less than four digits, we pad the output with
** leading zeroes to get the newline in the traditional place.
** The -4 ensures that we get four characters of output even if
** we call a strftime variant that produces fewer characters for some years.
** This conforms to recent ISO C and POSIX standards, which say behavior
** is undefined when the year is less than 1000 or greater than 9999.
*/
static char const ASCTIME_FMT[] = "%s %s%3d %.2d:%.2d:%.2d %-4s\n";
/*
** For years that are more than four digits we put extra spaces before the year
** so that code trying to overwrite the newline won't end up overwriting
** a digit within a year and truncating the year (operating on the assumption
** that no output is better than wrong output).
*/
static char const ASCTIME_FMT_B[] = "%s %s%3d %.2d:%.2d:%.2d %s\n";

enum { STD_ASCTIME_BUF_SIZE = 26 };
/*
** Big enough for something such as
Expand All @@ -50,14 +30,24 @@ enum { STD_ASCTIME_BUF_SIZE = 26 };
*/
static char buf_asctime[2*3 + 5*INT_STRLEN_MAXIMUM(int) + 7 + 2 + 1 + 1];

/* A similar buffer for ctime.
C89 requires that they be the same buffer.
This requirement was removed in C99, so support it only if requested,
as support is more likely to lead to bugs in badly written programs. */
#if SUPPORT_C89
# define buf_ctime buf_asctime
#else
static char buf_ctime[sizeof buf_asctime];
/* On pre-C99 platforms, a snprintf substitute good enough for us. */
#if !HAVE_SNPRINTF
# include <stdarg.h>
ATTRIBUTE_FORMAT((printf, 3, 4)) static int
my_snprintf(char *s, size_t size, char const *format, ...)
{
int n;
va_list args;
char stackbuf[sizeof buf_asctime];
va_start(args, format);
n = vsprintf(stackbuf, format, args);
va_end (args);
if (0 <= n && n < size)
memcpy (s, stackbuf, n + 1);
return n;
}
# undef snprintf
# define snprintf my_snprintf
#endif

/* Publish asctime_r and ctime_r only when supporting older POSIX. */
Expand All @@ -84,38 +74,59 @@ asctime_r(struct tm const *restrict timeptr, char *restrict buf)
};
register const char * wn;
register const char * mn;
char year[INT_STRLEN_MAXIMUM(int) + 2];
char result[sizeof buf_asctime];
int year, mday, hour, min, sec;
long long_TM_YEAR_BASE = TM_YEAR_BASE;
size_t bufsize = (buf == buf_asctime
? sizeof buf_asctime : STD_ASCTIME_BUF_SIZE);

if (timeptr == NULL) {
strcpy(buf, "??? ??? ?? ??:??:?? ????\n");
/* Set errno now, since strcpy might change it in
POSIX.1-2017 and earlier. */
errno = EINVAL;
return strcpy(buf, "??? ??? ?? ??:??:?? ????\n");
return buf;
}
if (timeptr->tm_wday < 0 || timeptr->tm_wday >= DAYSPERWEEK)
wn = "???";
else wn = wday_name[timeptr->tm_wday];
if (timeptr->tm_mon < 0 || timeptr->tm_mon >= MONSPERYEAR)
mn = "???";
else mn = mon_name[timeptr->tm_mon];
/*
** Use strftime's %Y to generate the year, to avoid overflow problems
** when computing timeptr->tm_year + TM_YEAR_BASE.
** Assume that strftime is unaffected by other out-of-range members
** (e.g., timeptr->tm_mday) when processing "%Y".
*/
strftime(year, sizeof year, "%Y", timeptr);
/*
** We avoid using snprintf since it's not available on all systems.
*/
sprintf(result,
((strlen(year) <= 4) ? ASCTIME_FMT : ASCTIME_FMT_B),
wn, mn,
timeptr->tm_mday, timeptr->tm_hour,
timeptr->tm_min, timeptr->tm_sec,
year);
if (strlen(result) < STD_ASCTIME_BUF_SIZE
|| buf == buf_ctime || buf == buf_asctime)
return strcpy(buf, result);

year = timeptr->tm_year;
mday = timeptr->tm_mday;
hour = timeptr->tm_hour;
min = timeptr->tm_min;
sec = timeptr->tm_sec;

/* Vintage programs are coded for years that are always four bytes long
and may assume that the newline always lands in the same place.
For years that are less than four bytes, pad the output with
leading zeroes to get the newline in the traditional place.
For years longer than four bytes, put extra spaces before the year
so that vintage code trying to overwrite the newline
won't overwrite a digit within a year and truncate the year,
using the principle that no output is better than wrong output.
This conforms to ISO C and POSIX standards, which say behavior
is undefined when the year is less than 1000 or greater than 9999.
Also, avoid overflow when formatting tm_year + TM_YEAR_BASE. */

if ((year <= LONG_MAX - TM_YEAR_BASE
? snprintf (buf, bufsize,
((-999 - TM_YEAR_BASE <= year
&& year <= 9999 - TM_YEAR_BASE)
? "%s %s%3d %.2d:%.2d:%.2d %04ld\n"
: "%s %s%3d %.2d:%.2d:%.2d %ld\n"),
wn, mn, mday, hour, min, sec,
year + long_TM_YEAR_BASE)
: snprintf (buf, bufsize,
"%s %s%3d %.2d:%.2d:%.2d %d%d\n",
wn, mn, mday, hour, min, sec,
year / 10 + TM_YEAR_BASE / 10,
year % 10))
< bufsize)
return buf;
else {
errno = EOVERFLOW;
return NULL;
Expand All @@ -140,5 +151,8 @@ ctime_r(const time_t *timep, char *buf)
char *
ctime(const time_t *timep)
{
return ctime_r(timep, buf_ctime);
/* Do not call localtime_r, as C23 requires ctime to initialize the
static storage that localtime updates. */
struct tm *tmp = localtime(timep);
return tmp ? asctime(tmp) : NULL;
}
Loading

0 comments on commit 7abdc14

Please sign in to comment.