Index: ChangeLog =================================================================== RCS file: /home/cvs/fsf/libc/ChangeLog,v retrieving revision 1.780.2.46 diff -u -r1.780.2.46 ChangeLog --- ChangeLog 1997/09/09 01:45:11 1.780.2.46 +++ ChangeLog 1997/09/10 02:44:11 @@ -1,3 +1,49 @@ +1997-09-10 04:42 Ulrich Drepper + + * sysdeps/unix/sysv/linux/netinet/ip_fw.h (struct ip_fw): Correct + type of fw_pcnt and fw_bcnt fields to match kernel. + Patch by a sun . + +1997-09-09 22:11 Ulrich Drepper + + * sysdeps/posix/getcwd.c: Correct test for too small buffer. + Reported by Erik Troan . + +1997-09-06 Paul Eggert + + Fix gmtime so that it reports leap seconds when TZ + indicates that leap seconds are desired. + + * time/gmtime.c (): Remove unnecessary include. + (gmtime): Put after gmtime_r, to help the compiler inline. + (__tz_convert): New decl. + (gmtime_r): Use __tz_convert instead of __offtime, + so that leap seconds are handled correctly. + + * time/localtime.c (, ): Remove includes that + are now unnecessary. + (__tzset_internal, __tz_compute, __tzfile_compute, __use_tzfile, + __tzset_lock): Remove extern decls that are now unnecessary. + (localtime_internal): Moved to __tz_convert in tzset.c. + so that localtime and gmtime can both use it easily. + (localtime): Put after localtime_r, to help the compiler inline. + (localtime_r): Use __tz_convert instead of localtime_internal. + + * time/strftime.c (__tz_compute): Remove unused (and now incorrect) + decl. + + * time/tzfile.c (__tzfile_compute): New arg USE_LOCALTIME. + + * time/tzset.c (): Include. + (_tmbuf): New decl. + (__tzfile_compute): New function. + (tz_compute): Renamed from __tz_compute. No longer extern. + Remove redundant call to tzset_internal. + (tzset_internal): Renamed from __tzset_internal. No longer extern. + (tzset_lock): Renamed from __tzset_lock. No longer extern. + (__tz_convert): New function, containing functionality of old + localtime_internal function, plus locking and optional UTC. + 1997-09-06 Paul Eggert * tzfile.c (__tzfile_read): Don't read a file if TZ is the empty Index: sysdeps/posix/getcwd.c =================================================================== RCS file: /home/cvs/fsf/libc/sysdeps/posix/getcwd.c,v retrieving revision 1.25 diff -u -r1.25 getcwd.c --- sysdeps/posix/getcwd.c 1997/02/10 03:19:27 1.25 +++ sysdeps/posix/getcwd.c 1997/09/09 20:57:05 @@ -326,7 +326,7 @@ { size_t namlen = _D_EXACT_NAMLEN (d); - if ((size_t) (pathp - path) < namlen) + if ((size_t) (pathp - path) <= namlen) { if (buf != NULL) { Index: sysdeps/unix/sysv/linux/netinet/ip_fw.h =================================================================== RCS file: /home/cvs/fsf/libc/sysdeps/unix/sysv/linux/netinet/ip_fw.h,v retrieving revision 1.1.2.3 diff -u -r1.1.2.3 ip_fw.h --- sysdeps/unix/sysv/linux/netinet/ip_fw.h 1997/08/05 23:36:05 1.1.2.3 +++ sysdeps/unix/sysv/linux/netinet/ip_fw.h 1997/09/10 02:41:46 @@ -70,7 +70,7 @@ /* count of 0 means match all ports) */ #define IP_FW_MAX_PORTS 10 /* A reasonable maximum */ u_int16_t fw_pts[IP_FW_MAX_PORTS]; /* Array of port numbers to match */ - u_int32_t fw_pcnt, fw_bcnt; /* Packet and byte counters */ + unsigned long int fw_pcnt, fw_bcnt; /* Packet and byte counters */ u_int8_t fw_tosand, fw_tosxor; /* Revised packet priority */ char fw_vianame[IFNAMSIZ]; /* name of interface "via" */ }; Index: time/README =================================================================== RCS file: /home/cvs/fsf/libc/time/README,v retrieving revision 1.2 retrieving revision 1.2.4.1 diff -u -r1.2 -r1.2.4.1 --- time/README 1997/01/25 02:36:37 1.2 +++ README 1997/09/09 12:43:57 1.2.4.1 @@ -3,7 +3,7 @@ `zdump.c' `tzselect.ksh' `checktab.awk' -come from the tzcode1997a package by Arthur David Olsen et.al. +come from the tzcode1997g package by Arthur David Olsen et.al. The files `africa' @@ -25,4 +25,4 @@ `zone.tab' `leapseconds' `yearistype' -come from the tzdata1997a package by Arthur David Olsen et.al. +come from the tzdata1997h package by Arthur David Olsen et.al. Index: time/africa =================================================================== RCS file: /home/cvs/fsf/libc/time/africa,v retrieving revision 1.8.4.2 retrieving revision 1.8.4.3 diff -u -r1.8.4.2 -r1.8.4.3 --- time/africa 1997/08/05 23:36:11 1.8.4.2 +++ africa 1997/09/09 12:43:57 1.8.4.3 @@ -1,4 +1,4 @@ -# @(#)africa 7.18 +# @(#)africa 7.19 # This data is by no means authoritative; if you think you know better, # go ahead and edit the file (and please send any changes to @@ -26,85 +26,6 @@ # A reliable and entertaining source about time zones is # Derek Howse, Greenwich time and the discovery of the longitude, # Oxford University Press (1980). -# -# I added so many Zone names that the old, mostly flat name space was unwieldy. -# So I renamed the Zones to have the form AREA/LOCATION, where -# AREA is the name of a continent or ocean, and -# LOCATION is the name of a specific location within that region. -# For example, the old zone name `Egypt' is now `Africa/Cairo'. -# -# Here are the general rules I used for choosing location names, -# in decreasing order of importance: -# -# Use only valid Posix file names. Use only Ascii letters, digits, `.', -# `-' and `_'. Do not exceed 14 characters or start with `-'. -# E.g. prefer `Brunei' to `Bandar_Seri_Begawan'. -# Include at least one location per time zone rule set per country. -# One such location is enough. -# If all the clocks in a country's region have agreed since 1970, -# don't bother to include more than one location -# even if subregions' clocks disagreed before 1970. -# Otherwise these tables would become annoyingly large. -# If a name is ambiguous, use a less ambiguous alternative; -# e.g. many cities are named San Jose and Georgetown, so -# prefer `Costa_Rica' to `San_Jose' and `Guyana' to `Georgetown'. -# Keep locations compact. Use cities or small islands, not countries -# or regions, so that any future time zone changes do not split -# locations into different time zones. E.g. prefer `Paris' -# to `France', since France has had multiple time zones. -# Use traditional English spelling, e.g. prefer `Rome' to `Roma', and -# prefer `Athens' to the true name (which uses Greek letters). -# The Posix file name restrictions encourage this rule. -# Use the most populous among locations in a country's time zone, -# e.g. prefer `Shanghai' to `Beijing'. Among locations with -# similar populations, pick the best-known location, -# e.g. prefer `Rome' to `Milan'. -# Use the singular form, e.g. prefer `Canary' to `Canaries'. -# Omit common suffixes like `_Islands' and `_City', unless that -# would lead to ambiguity. E.g. prefer `Cayman' to -# `Cayman_Islands' and `Guatemala' to `Guatemala_City', -# but prefer `Mexico_City' to `Mexico' because the country -# of Mexico has several time zones. -# Use `_' to represent a space. -# Omit `.' from abbreviations in names, e.g. prefer `St_Helena' -# to `St._Helena'. -# -# For time zone abbreviations like `EST' I used the following rules, -# in decreasing order of importance: -# -# Use abbreviations that consist of 3 or more upper-case Ascii letters, -# except use "___" for locations while uninhabited. -# Posix.1 requires at least 3 characters, and the restriction to -# upper-case Ascii letters follows most traditions. -# Previous editions of this database also used characters like -# ' ' and '?', but these characters have a special meaning to -# the shell and cause commands like -# set `date` -# to have unexpected effects. In theory, the character set could -# be !%./@A-Z^_a-z{}, but these tables use only upper-case -# Ascii letters (and "___"). -# Use abbreviations that are in common use among English-speakers, -# e.g. `EST' for Eastern Standard Time in North America. -# We assume that applications translate them to other languages -# as part of the normal localization process; for example, -# a French application might translate `EST' to `HNE'. -# For zones whose times are taken from a city's longitude, use the -# traditional xMT notation, e.g. `PMT' for Paris Mean Time. -# The only name like this in current use is `GMT'. -# If there is no common English abbreviation, abbreviate the English -# translation of the usual phrase used by native speakers. -# If this is not available or is a phrase mentioning the country -# (e.g. ``Cape Verde Time''), then: -# -# When a country has a single or principal time zone region, -# append `T' to the country's ISO code, e.g. `CVT' for -# Cape Verde Time. For summer time append `ST'; -# for double summer time append `DST'; etc. -# When a country has multiple time zones, take the first three -# letters of an English place name identifying each zone -# and then append `T', `ST', etc. as before; -# e.g. `MOSST' for MOScow Summer Time. -# # # For Africa I invented the following time zone abbreviations. # LMT Local Mean Time Index: time/europe =================================================================== RCS file: /home/cvs/fsf/libc/time/europe,v retrieving revision 1.14.4.3 retrieving revision 1.14.4.4 diff -u -r1.14.4.3 -r1.14.4.4 --- time/europe 1997/08/05 23:36:14 1.14.4.3 +++ europe 1997/09/09 12:43:58 1.14.4.4 @@ -1,4 +1,4 @@ -# @(#)europe 7.45 +# @(#)europe 7.46 # This data is by no means authoritative; if you think you know better, # go ahead and edit the file (and please send any changes to @@ -630,18 +630,18 @@ # came into force on 16 November. It restates the dates from the EC # seventh Summer Time Directive.... # -# From Peter Ilieve (1997-03-28): -# The [European] Transport Council discussed the proposed Eighth Directive -# on 11 March and agreed [to] it, so it moves forward to the next stage, -# from a Commission proposal to a Common Position.... What this means is: -# -# - The eighth directive proposal rules have been accepted. -# These are the same as the current rules (last Sunday in March and last -# Sunday in October). The rules will run until 2001. -# -# - The French have had their request to abandon summer time turned down. -# They have been promised some sort of review in 1999 which might change -# the rules for 2000 and 2001. +# From Peter Ilieve (1997-08-06): +# I now have a copy of the ... Eighth Directive 97/44/EC of the European +# Parliament and of the Council of 22 July 1997 on summer-time arrangements. +# It runs for 4 years, 1998--2001, and confirms the current rules of +# last Sunday in March to last Sunday in October.... +# The directive does not apply in overseas territories of the Member States. +# It says the Commission should produce a proposal for 2002 and beyond +# by 1 Jan 2000 and this should be adopted by 1 Jan 2001. I doubt that +# this will happen though.... +# There is no mention of the French desire to abandon the whole idea. +# France has had a change of government recently so maybe it will +# be quietly dropped. # From Peter Ilieve (1994-03-28): # The [GB-Eire] end date of 22 October [1995] conflicts with your current rule @@ -667,12 +667,12 @@ # Also, for lack of other data, we'll follow Shanks for Eire in 1940-1948. # # Given Peter Ilieve's comments, the following claims by Shanks are incorrect: -# * Wales did not switch from GMT to daylight savings time until +# * Wales did not switch from GMT to daylight saving time until # 1921 Apr 3, when they began to conform with the rest of Great Britain. # Actually, Wales was identical after 1880. # * Eire had two transitions on 1916 Oct 1. # It actually just had one transition. -# * Northern Ireland used single daylight savings time throughout WW II. +# * Northern Ireland used single daylight saving time throughout WW II. # Actually, it conformed to Britain. # * GB-Eire changed standard time to 1 hour ahead of GMT on 1968-02-18. # Actually, that date saw the usual switch to summer time. @@ -681,7 +681,7 @@ # The following claims by Shanks are possible though doubtful; # we'll ignore them for now. # * Jersey, Guernsey, and the Isle of Man did not switch from GMT -# to daylight savings time until 1921 Apr 3, when they began to +# to daylight saving time until 1921 Apr 3, when they began to # conform with Great Britain. # * Dublin's 1971-10-31 switch was at 02:00, even though London's was 03:00. # @@ -1047,7 +1047,7 @@ 1:00 - CET 1941 Apr 18 23:00 1:00 C-Eur CE%sT 1945 May 8 2:00s 1:00 1:00 CEST 1945 Sep 16 2:00s - 1:00 - CET 1982 Oct 11 + 1:00 - CET 1982 Nov 27 1:00 EU CE%sT # Bulgaria @@ -1073,7 +1073,7 @@ 1:00 - CET 1941 Apr 18 23:00 1:00 C-Eur CE%sT 1945 May 8 2:00s 1:00 1:00 CEST 1945 Sep 16 2:00s - 1:00 - CET 1982 Oct 11 + 1:00 - CET 1982 Nov 27 1:00 EU CE%sT # Czech Republic @@ -1572,7 +1572,7 @@ 1:00 - CET 1941 Apr 18 23:00 1:00 C-Eur CE%sT 1945 May 8 2:00s 1:00 1:00 CEST 1945 Sep 16 2:00s - 1:00 - CET 1982 Oct 11 + 1:00 - CET 1982 Nov 27 1:00 EU CE%sT # Malta @@ -1968,7 +1968,7 @@ 1:00 - CET 1941 Apr 18 23:00 1:00 C-Eur CE%sT 1945 May 8 2:00s 1:00 1:00 CEST 1945 Sep 16 2:00s - 1:00 - CET 1982 Oct 11 + 1:00 - CET 1982 Nov 27 1:00 EU CE%sT # Spain @@ -2209,9 +2209,9 @@ 1:00 C-Eur CE%sT 1945 May 8 2:00s 1:00 1:00 CEST 1945 Sep 16 2:00s # Metod Kozelj reports that the legal date of -# transition to EU rules was 1982-10-11, for all of Yugoslavia at the time. +# transition to EU rules was 1982-11-27, for all of Yugoslavia at the time. # Shanks doesn't give as much detail, so go with Kozelj. - 1:00 - CET 1982 Oct 11 + 1:00 - CET 1982 Nov 27 1:00 EU CE%sT ############################################################################### Index: time/gmtime.c =================================================================== RCS file: /home/cvs/fsf/libc/time/gmtime.c,v retrieving revision 1.8 retrieving revision 1.8.4.1 diff -u -r1.8 -r1.8.4.1 --- time/gmtime.c 1997/01/21 06:10:34 1.8 +++ gmtime.c 1997/09/09 12:43:58 1.8.4.1 @@ -1,4 +1,5 @@ -/* Copyright (C) 1991, 1993, 1995, 1996, 1997 Free Software Foundation, Inc. +/* Convert `time_t' to `struct tm' in UTC. + Copyright (C) 1991, 1993, 1995, 1996, 1997 Free Software Foundation, Inc. This file is part of the GNU C Library. The GNU C Library is free software; you can redistribute it and/or @@ -16,19 +17,14 @@ write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -#include #include /* Defined in localtime.c. */ extern struct tm _tmbuf; -/* Return the `struct tm' representation of *T in UTC. */ -struct tm * -gmtime (t) - const time_t *t; -{ - return __gmtime_r (t, &_tmbuf); -} +/* Prototype for the internal function to get information based on TZ. */ +extern struct tm *__tz_convert __P ((const time_t *t, int use_localtime, + struct tm *tp)); /* Return the `struct tm' representation of *T in UTC, @@ -38,12 +34,15 @@ const time_t *t; struct tm *tp; { - __offtime (t, 0L, tp); + return __tz_convert (t, 0, tp); +} +weak_alias (__gmtime_r, gmtime_r) - tp->tm_isdst = 0; - tp->tm_gmtoff = 0L; - tp->tm_zone = "GMT"; - return tp; +/* Return the `struct tm' representation of *T in UTC. */ +struct tm * +gmtime (t) + const time_t *t; +{ + return __tz_convert (t, 0, &_tmbuf); } -weak_alias (__gmtime_r, gmtime_r) Index: time/iso3166.tab =================================================================== RCS file: /home/cvs/fsf/libc/time/iso3166.tab,v retrieving revision 1.1.4.1 retrieving revision 1.1.4.2 diff -u -r1.1.4.1 -r1.1.4.2 --- time/iso3166.tab 1997/08/05 23:36:14 1.1.4.1 +++ iso3166.tab 1997/09/09 12:43:58 1.1.4.2 @@ -7,6 +7,9 @@ # 2. The usual English name for the country, # chosen so that alphabetic sorting of subsets produces helpful lists. # +# For France in Europe, we follow common practice and use FR, +# even though FX might be more technically correct. +# # Columns are separated by a single tab. # The table is sorted by country code. # @@ -86,6 +89,7 @@ FM Micronesia FO Faeroe Islands FR France +FX France, Metropolitan GA Gabon GB Britain (UK) GD Grenada Index: time/localtime.c =================================================================== RCS file: /home/cvs/fsf/libc/time/localtime.c,v retrieving revision 1.20 retrieving revision 1.20.4.1 diff -u -r1.20 -r1.20.4.1 --- time/localtime.c 1997/01/06 22:07:26 1.20 +++ localtime.c 1997/09/09 12:43:58 1.20.4.1 @@ -17,106 +17,33 @@ write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -#include #include -#include /* The C Standard says that localtime and gmtime return the same pointer. */ struct tm _tmbuf; /* Prototype for the internal function to get information based on TZ. */ -extern void __tzset_internal __P ((int always)); -extern int __tz_compute __P ((time_t timer, struct tm *tp)); -extern int __tzfile_compute __P ((time_t timer, - long int *leap_correct, int *leap_hit)); - -extern int __use_tzfile; - -/* This lock is defined in tzset.c and locks all the data defined there - and in tzfile.c; the internal functions do no locking themselves. - This lock is only taken here and in `tzset'. */ -__libc_lock_define (extern, __tzset_lock) - - -/* Return the `struct tm' representation of *TIMER in the local timezone. */ -static struct tm * -localtime_internal (const time_t *timer, struct tm *tp) -{ - long int leap_correction; - int leap_extra_secs; - - if (timer == NULL) - { - __set_errno (EINVAL); - return NULL; - } - - if (__use_tzfile) - { - if (! __tzfile_compute (*timer, &leap_correction, &leap_extra_secs)) - tp = NULL; - } - else - { - tp = __gmtime_r (timer, tp); - if (tp && ! __tz_compute (*timer, tp)) - tp = NULL; - leap_correction = 0L; - leap_extra_secs = 0; - } - - if (tp) - { - __offtime (timer, __timezone - leap_correction, tp); - tp->tm_sec += leap_extra_secs; - tp->tm_isdst = __daylight; - tp->tm_gmtoff = __timezone; - tp->tm_zone = __tzname[__daylight]; - } +extern struct tm *__tz_convert __P ((const time_t *t, int use_localtime, + struct tm *tp)); - return tp; -} -/* POSIX.1 8.3.7.2 says that localtime_r is not required to set - tzname. This is a good idea since this allows at least a bit more - parallelism. */ - +/* Return the `struct tm' representation of *T in local time, + using *TP to store the result. */ struct tm * -localtime (timer) - const time_t *timer; +__localtime_r (t, tp) + const time_t *t; + struct tm *tp; { - struct tm *result; - - __libc_lock_lock (__tzset_lock); - - /* Update internal database according to current TZ setting. */ - __tzset_internal (1); - - result = localtime_internal (timer, &_tmbuf); - - __libc_lock_unlock (__tzset_lock); - - return result; + return __tz_convert (t, 1, tp); } +weak_alias (__localtime_r, localtime_r) +/* Return the `struct tm' representation of *T in local time. */ struct tm * -__localtime_r (timer, tp) - const time_t *timer; - struct tm *tp; +localtime (t) + const time_t *t; { - struct tm *result; - - __libc_lock_lock (__tzset_lock); - - /* Make sure the database is initialized. */ - __tzset_internal (0); - - result = localtime_internal (timer, tp); - - __libc_lock_unlock (__tzset_lock); - - return result; + return __tz_convert (t, 1, &_tmbuf); } -weak_alias (__localtime_r, localtime_r) Index: time/northamerica =================================================================== RCS file: /home/cvs/fsf/libc/time/northamerica,v retrieving revision 1.14.4.1 retrieving revision 1.14.4.2 diff -u -r1.14.4.1 -r1.14.4.2 --- time/northamerica 1997/04/05 00:40:14 1.14.4.1 +++ northamerica 1997/09/09 12:43:59 1.14.4.2 @@ -1,4 +1,4 @@ -# @(#)northamerica 7.31 +# @(#)northamerica 7.32 # also includes Central America and the Caribbean # This data is by no means authoritative; if you think you know better, @@ -1249,8 +1249,11 @@ -4:00 - AST # Montserrat +# From Paul Eggert (1997-08-31): +# Recent volcanic eruptions have forced evacuation of Plymouth, the capital. +# Luckily, Olveston, the current de facto capital, has the same longitude. # Zone NAME GMTOFF RULES FORMAT [UNTIL] -Zone America/Montserrat -4:08:52 - LMT 1911 Jul 1 0:01 # Plymouth +Zone America/Montserrat -4:08:52 - LMT 1911 Jul 1 0:01 # Olveston -4:00 - AST # Nicaragua Index: time/southamerica =================================================================== RCS file: /home/cvs/fsf/libc/time/southamerica,v retrieving revision 1.8.4.1 retrieving revision 1.8.4.2 diff -u -r1.8.4.1 -r1.8.4.2 --- time/southamerica 1997/04/05 00:40:15 1.8.4.1 +++ southamerica 1997/09/09 12:43:59 1.8.4.2 @@ -1,4 +1,4 @@ -# @(#)southamerica 7.17 +# @(#)southamerica 7.18 # This data is by no means authoritative; if you think you know better, # go ahead and edit the file (and please send any changes to @@ -533,7 +533,9 @@ Rule Uruguay 1989 only - Oct 29 0:00 1:00 S Rule Uruguay 1990 1992 - Mar Sun>=1 0:00 0 - Rule Uruguay 1990 1991 - Oct Sun>=21 0:00 1:00 S -Rule Uruguay 1992 1993 - Oct Sun>=15 0:00 1:00 S +# Shanks's 4th edition (1995) says no DST was observed in 1990/1 and 1991/2, +# and that 1992/3's DST was from 10-25 to 03-01. Go with IATA. +Rule Uruguay 1992 only - Oct 18 0:00 1:00 S Rule Uruguay 1993 only - Feb 28 0:00 0 - # Zone NAME GMTOFF RULES FORMAT [UNTIL] Zone America/Montevideo -3:44:44 - LMT 1898 Jun 28 Index: time/strftime.c =================================================================== RCS file: /home/cvs/fsf/libc/time/strftime.c,v retrieving revision 1.35.4.3 retrieving revision 1.35.4.4 diff -u -r1.35.4.3 -r1.35.4.4 --- time/strftime.c 1997/08/05 23:36:16 1.35.4.3 +++ strftime.c 1997/09/09 12:44:00 1.35.4.4 @@ -132,7 +132,6 @@ #ifdef _LIBC # define gmtime_r __gmtime_r # define localtime_r __localtime_r -extern int __tz_compute __P ((time_t timer, const struct tm *tm)); # define tzname __tzname # define tzset __tzset #else Index: time/tzfile.c =================================================================== RCS file: /home/cvs/fsf/libc/time/tzfile.c,v retrieving revision 1.23.4.3 retrieving revision 1.23.4.4 diff -u -r1.23.4.3 -r1.23.4.4 --- time/tzfile.c 1997/09/09 01:45:54 1.23.4.3 +++ tzfile.c 1997/09/09 12:44:00 1.23.4.4 @@ -43,7 +43,7 @@ long int change; /* Seconds of correction to apply. */ }; -extern const char * __tzstring (const char *); /* Defined in tzset.c. */ +extern char * __tzstring (const char *); /* Defined in tzset.c. */ static struct ttinfo *find_transition (time_t timer); static void compute_tzname_max (size_t); @@ -411,19 +411,23 @@ } int -__tzfile_compute (time_t timer, long int *leap_correct, int *leap_hit) +__tzfile_compute (time_t timer, int use_localtime, + long int *leap_correct, int *leap_hit) { - struct ttinfo *info; register size_t i; - info = find_transition (timer); - __daylight = info->isdst; - __timezone = info->offset; - for (i = 0; i < num_types && i < sizeof (__tzname) / sizeof (__tzname[0]); - ++i) - __tzname[types[i].isdst] = &zone_names[types[i].idx]; - if (info->isdst < sizeof (__tzname) / sizeof (__tzname[0])) - __tzname[info->isdst] = &zone_names[info->idx]; + if (use_localtime) + { + struct ttinfo *info = find_transition (timer); + __daylight = info->isdst; + __timezone = info->offset; + for (i = 0; + i < num_types && i < sizeof (__tzname) / sizeof (__tzname[0]); + ++i) + __tzname[types[i].isdst] = &zone_names[types[i].idx]; + if (info->isdst < sizeof (__tzname) / sizeof (__tzname[0])) + __tzname[info->isdst] = &zone_names[info->idx]; + } *leap_correct = 0L; *leap_hit = 0; Index: time/tzset.c =================================================================== RCS file: /home/cvs/fsf/libc/time/tzset.c,v retrieving revision 1.41.4.4 diff -u -r1.41.4.4 tzset.c --- time/tzset.c 1997/09/09 01:45:55 1.41.4.4 +++ time/tzset.c 1997/09/09 13:40:39 @@ -17,6 +17,7 @@ Boston, MA 02111-1307, USA. */ #include +#include #include #include #include @@ -27,15 +28,19 @@ /* Defined in mktime.c. */ extern const unsigned short int __mon_yday[2][13]; +/* Defined in localtime.c. */ +extern struct tm _tmbuf; + #define NOID #include "tzfile.h" extern int __use_tzfile; extern void __tzfile_read __P ((const char *file)); +extern int __tzfile_compute __P ((time_t timer, int use_localtime, + long int *leap_correct, int *leap_hit)); extern void __tzfile_default __P ((const char *std, const char *dst, long int stdoff, long int dstoff)); -extern const char * __tzstring __P ((const char *string)); -extern int __tz_compute __P ((time_t timer, const struct tm *tm)); +extern char * __tzstring __P ((const char *string)); char *__tzname[2] = { (char *) "GMT", (char *) "GMT" }; int __daylight = 0; @@ -78,6 +83,8 @@ static int compute_change __P ((tz_rule *rule, int year)); +static int tz_compute __P ((time_t timer, const struct tm *tm)); +static void tzset_internal __P ((int always)); /* Header for a list of buffers containing time zone strings. */ struct tzstring_head @@ -102,7 +109,7 @@ /* Allocate a time zone string with given contents. The string will never be moved or deallocated. However, its contents may be shared with other such strings. */ -const char * +char * __tzstring (string) const char *string; { @@ -113,7 +120,7 @@ /* Look through time zone string list for a duplicate of this one. */ for (h = &tzstring_list.head; ; h = h->next) { - for (p = (char *) (h + 1); p[0] | p[1]; p++) + for (p = (char *) (h + 1); p[0] | p[1]; ++p) if (strcmp (p, string) == 0) return p; if (! h->next) @@ -122,7 +129,7 @@ /* No duplicate was found. Copy to the end of this buffer if there's room; otherwise, append a large-enough new buffer to the list and use it. */ - p++; + ++p; needed = strlen (string) + 2; /* Need 2 trailing '\0's after last string. */ if ((size_t) ((char *) (h + 1) + tzstring_last_buffer_size - p) < needed) @@ -137,16 +144,14 @@ p = (char *) (h + 1); } - strncpy (p, string, needed); - return p; + return strncpy (p, string, needed); } static char *old_tz = NULL; /* Interpret the TZ envariable. */ -void __tzset_internal __P ((int always)); -void -__tzset_internal (always) +static void +tzset_internal (always) int always; { static int is_initialized = 0; @@ -338,12 +343,9 @@ { register tz_rule *tzr = &tz_rules[whichrule]; - if (*tz == ',') - { - ++tz; - if (*tz == '\0') - return; - } + /* Ignore comma to support string following the incorrect + specification in early POSIX.1 printings. */ + tz += *tz == ','; /* Get the date of the change. */ if (*tz == 'J' || isdigit (*tz)) @@ -436,7 +438,7 @@ { __libc_lock_lock (tzset_lock); - __tzset_internal (0); + tzset_internal (0); __libc_lock_unlock (tzset_lock); @@ -531,13 +533,11 @@ /* Figure out the correct timezone for *TIMER and TM (which must be the same) and set `__tzname', `__timezone', and `__daylight' accordingly. Return nonzero on success, zero on failure. */ -int -__tz_compute (timer, tm) +static int +tz_compute (timer, tm) time_t timer; const struct tm *tm; { - __tzset_internal (0); - if (! compute_change (&tz_rules[0], 1900 + tm->tm_year) || ! compute_change (&tz_rules[1], 1900 + tm->tm_year)) return 0; @@ -568,7 +568,7 @@ { __libc_lock_lock (tzset_lock); - __tzset_internal (1); + tzset_internal (1); if (!__use_tzfile) { @@ -580,3 +580,64 @@ __libc_lock_unlock (tzset_lock); } weak_alias (__tzset, tzset) + +/* Return the `struct tm' representation of *TIMER in the local timezone. + Use local time if USE_LOCALTIME is nonzero, UTC otherwise. */ +struct tm * +__tz_convert (const time_t *timer, int use_localtime, struct tm *tp) +{ + long int leap_correction; + int leap_extra_secs; + + if (timer == NULL) + { + __set_errno (EINVAL); + return NULL; + } + + __libc_lock_lock (tzset_lock); + + /* Update internal database according to current TZ setting. + POSIX.1 8.3.7.2 says that localtime_r is not required to set tzname. + This is a good idea since this allows at least a bit more parallelism. + By analogy we apply the same rule to gmtime_r. */ + tzset_internal (tp == &_tmbuf); + + if (__use_tzfile) + { + if (! __tzfile_compute (*timer, use_localtime, + &leap_correction, &leap_extra_secs)) + tp = NULL; + } + else + { + __offtime (timer, 0, tp); + if (! tz_compute (*timer, tp)) + tp = NULL; + leap_correction = 0L; + leap_extra_secs = 0; + } + + if (tp) + { + if (use_localtime) + { + tp->tm_isdst = __daylight; + tp->tm_zone = __tzname[__daylight]; + tp->tm_gmtoff = __timezone; + } + else + { + tp->tm_isdst = 0; + tp->tm_zone = "GMT"; + tp->tm_gmtoff = 0L; + } + + __offtime (timer, tp->tm_gmtoff - leap_correction, tp); + tp->tm_sec += leap_extra_secs; + } + + __libc_lock_unlock (tzset_lock); + + return tp; +} Index: time/zone.tab =================================================================== RCS file: /home/cvs/fsf/libc/time/zone.tab,v retrieving revision 1.3.4.2 retrieving revision 1.3.4.3 diff -u -r1.3.4.2 -r1.3.4.3 --- time/zone.tab 1997/08/05 23:36:17 1.3.4.2 +++ zone.tab 1997/09/09 12:44:00 1.3.4.3 @@ -231,7 +231,7 @@ MP +1512+14545 Pacific/Saipan MQ +1436-06105 America/Martinique MR +1806-01557 Africa/Nouakchott -MS +1642-06213 America/Montserrat +MS +1644-06213 America/Montserrat MT +3554+01431 Europe/Malta MU -2010+05730 Indian/Mauritius MV +0410+07330 Indian/Maldives