Section: 30.11.2.1 [time.zone.db.tzdb] Status: New Submitter: Jonathan Wakely Opened: 2025-02-22 Last modified: 2025-02-24
Priority: Not Prioritized
View all issues with New status.
Discussion:
Since
October 2022
the IANA Time Zone Database's tzfile data format allows a Link to refer
to another Link, instead of referring directly to a Zone.
The zic(8)
man page says:
The TARGET field should appear as the NAME field in some zone line or as the LINK-NAME field in some link line. The LINK-NAME field is used as an alternative name for that zone; it has the same syntax as a zone line's NAME field. Links can chain together, although the behavior is unspecified if a chain of one or more links does not terminate in a Zone name.Because chains of links were introduced to
tzfile after chrono::tzdb
was standardized, C++ does not properly support chains of links.
The time_zone_link::target() member function is required to return
"The name of the time_zone for which this time_zone_link provides
an alternative name."
This doesn't allow returning the name of another time_zone_link,
which implies that the implementation should flatten a series of links so
that the target is a time_zone. However, this discards information which
is present in the tzdb, so that the information exposed to a C++ program
does not preserve the original structure of a chain of links.
The standard could be adjusted to support chains of links by allowing
time_zone_link::target() to refer to another link, and then altering the
algorithm used by tzdb::locate_zone(string_view) to find a time_zone from
a name that might be a zone or a link.
Proposed resolution:
This wording is relative to N5001.
const time_zone* locate_zone(string_view tz_name) const;-2- Returns:
- (2.1) — If
zonescontains an elementtzfor whichtz.name() == tz_name, a pointer totz;- (2.2) — otherwise, if
linkscontains an elementtz_lfor whichtz_l.name() == tz_name, thena pointer to the elementthe result oftzof zones for whichtz.name() == tz_l.target()locate_zone(tz_l.target()). .[Note 1: A
time_zone_linkspecifies an alternative name for atime_zone. — end note]-3- Throws: If a
const time_zone*cannot be found as described in the Returns: element, throws aruntime_error.[Note 2: On non-exceptional return, the return value is always a pointer to a valid
time_zone. — end note]-?- Remarks: If both
zonesandlinkscontain elements that matchtz_namethen it is unspecified whether&tzorlocate_zone(tz_l.target())is returned.[Drafting note: This gives flexibility how to implement the lookup inlocate_zone.]
-1- A
time_zone_linkspecifies an alternative name for atime_zone.time_zone_linksare constructed when the time zone database is initialized. The name of atime_zone_linkcan be used as an argument totzdb::locate_zone(30.11.2.1 [time.zone.db.tzdb]). Atime_zone_linkcan refer directly to atime_zone, or to anothertime_zone_link, forming a chain of links.
-1- Returns: The alternative name for the time zone.string_view name() const noexcept;string_view target() const noexcept;-2- Returns: The name of the
time_zonefor which thistime_zone_linkprovides an alternative name or the name of anothertime_zone_link.[Note 1:
tzdb::locate_zonefollows a chain of links formed when a link's target is the name of atime_zone_link, throwing an exception if the chain of links does not terminate in atime_zone. — end note]