diff options
| author | Richard M. Stallman | 1996-06-05 15:08:18 +0000 |
|---|---|---|
| committer | Richard M. Stallman | 1996-06-05 15:08:18 +0000 |
| commit | aafe5147448734a0ef35deba8f8065f424e88343 (patch) | |
| tree | 2e47f199cb60ab3762ba8250086a00754c4d33fc /src | |
| parent | ed8a2c3a284a7371cccfd019c418f5ed47bddd46 (diff) | |
| download | emacs-aafe5147448734a0ef35deba8f8065f424e88343.tar.gz emacs-aafe5147448734a0ef35deba8f8065f424e88343.zip | |
(set_time_zone_rule):
Work around localtime cache bug in SunOS 4.1.3_U1 and SunOS 4.1.4.
Diffstat (limited to 'src')
| -rw-r--r-- | src/editfns.c | 48 |
1 files changed, 48 insertions, 0 deletions
diff --git a/src/editfns.c b/src/editfns.c index dc5e7988f23..c33a6acae8b 100644 --- a/src/editfns.c +++ b/src/editfns.c | |||
| @@ -939,11 +939,14 @@ set_time_zone_rule (tzstring) | |||
| 939 | int envptrs; | 939 | int envptrs; |
| 940 | char **from, **to, **newenv; | 940 | char **from, **to, **newenv; |
| 941 | 941 | ||
| 942 | /* Make the ENVIRON vector longer with room for TZSTRING. */ | ||
| 942 | for (from = environ; *from; from++) | 943 | for (from = environ; *from; from++) |
| 943 | continue; | 944 | continue; |
| 944 | envptrs = from - environ + 2; | 945 | envptrs = from - environ + 2; |
| 945 | newenv = to = (char **) xmalloc (envptrs * sizeof (char *) | 946 | newenv = to = (char **) xmalloc (envptrs * sizeof (char *) |
| 946 | + (tzstring ? strlen (tzstring) + 4 : 0)); | 947 | + (tzstring ? strlen (tzstring) + 4 : 0)); |
| 948 | |||
| 949 | /* Add TZSTRING to the end of environ, as a value for TZ. */ | ||
| 947 | if (tzstring) | 950 | if (tzstring) |
| 948 | { | 951 | { |
| 949 | char *t = (char *) (to + envptrs); | 952 | char *t = (char *) (to + envptrs); |
| @@ -952,6 +955,9 @@ set_time_zone_rule (tzstring) | |||
| 952 | *to++ = t; | 955 | *to++ = t; |
| 953 | } | 956 | } |
| 954 | 957 | ||
| 958 | /* Copy the old environ vector elements into NEWENV, | ||
| 959 | but don't copy the TZ variable. | ||
| 960 | So we have only one definition of TZ, which came from TZSTRING. */ | ||
| 955 | for (from = environ; *from; from++) | 961 | for (from = environ; *from; from++) |
| 956 | if (strncmp (*from, "TZ=", 3) != 0) | 962 | if (strncmp (*from, "TZ=", 3) != 0) |
| 957 | *to++ = *from; | 963 | *to++ = *from; |
| @@ -959,7 +965,49 @@ set_time_zone_rule (tzstring) | |||
| 959 | 965 | ||
| 960 | environ = newenv; | 966 | environ = newenv; |
| 961 | 967 | ||
| 968 | /* If we do have a TZSTRING, NEWENV points to the vector slot where | ||
| 969 | the TZ variable is stored. If we do not have a TZSTRING, | ||
| 970 | TO points to the vector slot which has the terminating null. */ | ||
| 971 | |||
| 962 | #ifdef LOCALTIME_CACHE | 972 | #ifdef LOCALTIME_CACHE |
| 973 | { | ||
| 974 | /* In SunOS 4.1.3_U1 and 4.1.4, if TZ has a value like | ||
| 975 | "US/Pacific" that loads a tz file, then changes to a value like | ||
| 976 | "XXX0" that does not load a tz file, and then changes back to | ||
| 977 | its original value, the last change is (incorrectly) ignored. | ||
| 978 | Also, if TZ changes twice in succession to values that do | ||
| 979 | not load a tz file, tzset can dump core (see Sun bug#1225179). | ||
| 980 | The following code works around these bugs. */ | ||
| 981 | |||
| 982 | /* These two values are known to load tz files in buggy implementations. | ||
| 983 | Their values shouldn't matter in non-buggy implementations. */ | ||
| 984 | char *tz1 = "TZ=GMT0"; | ||
| 985 | char *tz2 = "TZ=GMT1"; | ||
| 986 | |||
| 987 | if (tzstring) | ||
| 988 | { | ||
| 989 | /* Temporarily set TZ to a value that loads a tz file | ||
| 990 | and that differs from tzstring. */ | ||
| 991 | char *tz = *newenv; | ||
| 992 | *newenv = strcmp (tzstring, tz1 + 3) == 0 ? tz2 : tz1; | ||
| 993 | tzset (); | ||
| 994 | *newenv = tz; | ||
| 995 | } | ||
| 996 | else | ||
| 997 | { | ||
| 998 | /* The implied tzstring is unknown, so temporarily set TZ to | ||
| 999 | two different values that each load a tz file. */ | ||
| 1000 | *to = tz1; | ||
| 1001 | to[1] = 0; | ||
| 1002 | tzset (); | ||
| 1003 | *to = tz2; | ||
| 1004 | tzset (); | ||
| 1005 | *to = 0; | ||
| 1006 | } | ||
| 1007 | |||
| 1008 | /* Now TZ has the desired value, and tzset can be invoked safely. */ | ||
| 1009 | } | ||
| 1010 | |||
| 963 | tzset (); | 1011 | tzset (); |
| 964 | #endif | 1012 | #endif |
| 965 | } | 1013 | } |