[tz] tzcode history (was: Re: Java & Rearguard)
kre at munnari.OZ.AU
Tue Jun 4 05:39:48 UTC 2019
Date: Mon, 3 Jun 2019 14:19:30 -0700
From: Guy Harris <guy at alum.mit.edu>
Message-ID: <2E4D724F-E0E3-4E45-94B7-EF1F74A28A6D at alum.mit.edu>
| Whoever wrote that part of the Linux man page used a definition of
| "old systems" that means "systems starting with 4.2BSD"
Even more recent than that, perhaps 4.3 .. 4.2 didn't have all those
different timezone types, just US, Aust, and Europe (well, western
Europe, the eastern part couldn't license UNIX in any form so wasn't
| rather than, for example, "systems starting with Seventh Edition UNIX".
It was even worse earlier than that.
| The "tz_dstime" page was introduced in 4.2BSD;
First distributed, yes - it had been around a little before that
(it was one of my, shall we say, "less successful" inventions).
Also don't forget the timezone() function (which used TZNAME) to
allow users to decide what their timezone abbreviation(s) should be.
| V7 UNIX had a system that, to handle the full complexities of civil
| timekeeping in any given location, would require a source code change
| to ctime.c:
As did everything preceding the Olson code, in 4.2 BSD (and the earlier
netnews releases of it). The final TZ env var methods, even as they
are today, are insufficient.
| The standard-time offset from UTC could be obtained with an ftime()
| system call; changing it required recompiling the kernel,
| installing the new kernel, and rebooting.
And that was a 7th edition improvement - by then Bell Labs had recognised
that not all UNIX users were in the US Eastern timezone... Before then
there were global variables timezone and daylight in libc which could be
altered (by an application, or patched via a debugger in an application)
which set the timezone offset, and whether or not there was a seasonal
adjustment - which as you say, used the US rules at the time ... it is
perhaps worth mentioning that back when all this was happening predates
the mania with changing the rules every year or two, the rules were mostly
fairly stable. (That "timezone" is more or less the same variable that
we still have today, though "daylight" has fortunately vanished. Pity
that the BSD function timezone() didn't catch on more - not that it is
really useful, but it at least was incompatible with the variable, which,
along with tzname, is a truly stupid and useless idea ... the concept
that there is a single (global) static timezone offset that applies (to
any one timezone) and so can be made available in a global variable like
that is one of the incorrect assumptions that people tend to make about
the way that time works ("I have never seen different, so it must be
like this everywhere"). So is the "there are (at most) 2 different
abbreviations we can use, selectable based upon a boolean" nonsense.
| 4.2BSD improved this slightly.
Yes, very slightly... The one thing that it did that was worthwhile
was to make it more obvious that dealing with timezones needed more
than simply having localtime() in libc - that it was not sufficient to
simply assume that the US summer time rules applied everywhere.
| Meanwhile, at least according to a manual of System III vintage (it
| As per ctime(3), TZ could be set to specify [...]
This was always the wrong way, which is why none of it was copied in BSD,
as it required an env var to be set in order to work rationally, where
applications should be able to work properly (including use of localtime())
with a completely empty environment. Further its functionality (at the
time) was less, so that was simply ignored (though ado re-used the name of
the env var).
It is also worth noting that in all of this (pre Olson code) the definition
of a leap year was a ((y % 4) == 0) - which would have made a nice Y2100
problem if it had persisted. (And I wonder how much of the world's
software still believes that - 2100 will be the first year since the
(practical) invention of computers that it will not be true).
| By 1988, whatever BSD-based systems had the time zone stuff in
| gettimeofday()/settimeofday() had, I think, switched to using the
| tzdb code and data,
Yes, it was included in BSD in 4.3Tahoe - though lots of sites had
already picked it up from the usenet distributions (net.sources I think
it first appeared in - before the big usenet renaming anyway).
| so that the 4.2BSD-style way of specifying the time zone was provided
| only for backwards compatibility.
For API compatibility. Nothing used it any more. Which is why it still
exists today. Sad how some mistakes can linger.
Another thing worth mentioning here (making clear anyway) that back
in those days "recompile everything" (while it sounds horrible, and in
a sense was) was more or less a routine operation. Everyone had the
sources to everything (in the BSD world anyway, there was still very
little commercial unix use around) and a complete recompile of the universe
wasn't something that would take weeks (which compiling just some
application systems takes these days, on systems thousands of times faster)
but which would easily complete overnight.
| So it was 1) less capable than the SVR3.1 scheme and 2) not really
| being used any more, so there wasn't any reason for POSIX to
| standardize on it.
Fortunately they were not that stupid - it was a terrible idea.
Perhaps better than had previously existed (it stopped pretending
that the US was all that existed ... even admitted than there was
a southern hemisphere where summer and winter are switched around!)
but was definitly the wrong approach, for all kinds of reasons
(which are obvious now with hindsight - all I can say is that it
seemed like a good idea at the time.)
| I don't remember whether tzcode ever paid any attention to the
| 4.2BSD-style time zone setting on systems where it was available,
No, I don't think so, there was never a reason for that, the tzdb method
was better (so much better) and didn't need assistance from the kernel.
| I'm not sure what complexities, if any, the transition from the 4.2BSD
| scheme, on systems providing it, to the tzdb scheme added.
As I recall, none. Aside from one last "recompile everything" step to
adopt it (and if you started with a 4.3Tahoe or later release from Berkeley
you didn't even need to do that). Otherwise it was 100% functionally
compatible, and aside from the management issue of configuring it, the
change was mostly invisible to BSD applications (stuff that insisted on
using timezone (the variable) and tzname needed adapting - but always had).
| I forget when I added the initial support for POSIX-style TZ settings
| in tzcode;
As I remember it (and remembering the time scale for all of this happening
was within one decade) it was rather late in the process.
More information about the tz