ICU-5423 Information from the daylight global variable is insufficient.

Probing when daylight occurs seems more reliable.

X-SVN-Rev: 21837
This commit is contained in:
George Rhoten 2007-06-28 07:33:44 +00:00
parent 30c0f9f3af
commit 340f980d77
5 changed files with 51 additions and 201 deletions

View file

@ -551,15 +551,6 @@ uprv_tzset()
#endif
}
static int32_t uprv_daylight() {
#ifdef U_DAYLIGHT
return U_DAYLIGHT;
#else
/* Windows documentation says the default is 1. */
return 1;
#endif
}
U_CAPI int32_t U_EXPORT2
uprv_timezone()
{
@ -636,7 +627,7 @@ static UBool isValidOlsonID(const char *id) {
#define CONVERT_HOURS_TO_SECONDS(offset) (int32_t)(offset*3600)
typedef struct OffsetZoneMapping {
int32_t offsetSeconds;
int32_t daylightUsed;
int32_t daylightType; /* 1=daylight in June, 2=daylight in December*/
const char *stdID;
const char *dstID;
const char *olsonID;
@ -647,21 +638,25 @@ This list tries to disambiguate a set of abbreviated timezone IDs and offsets
and maps it to an Olson ID.
Before adding anything to this list, take a look at
icu/source/tools/tzcode/tz.alias
Sometimes no daylight savings is important to define due to aliases.
*/
static const struct OffsetZoneMapping OFFSET_ZONE_MAPPINGS[] = {
{-45900, 1, "CHAST", "CHADT", "Pacific/Chatham"},
{-45900, 2, "CHAST", "CHADT", "Pacific/Chatham"},
{-43200, 1, "PETT", "PETST", "Asia/Kamchatka"},
{-43200, 1, "NZST", "NZDT", "Pacific/Auckland"},
{-43200, 2, "NZST", "NZDT", "Pacific/Auckland"},
{-43200, 1, "ANAT", "ANAST", "Asia/Anadyr"},
{-39600, 1, "MAGT", "MAGST", "Asia/Magadan"},
/*{-36000, 1, "EST", "EST", "Australia/Melbourne"},*/
{-37800, 2, "LHST", "LHST", "Australia/Lord_Howe"},
{-36000, 2, "EST", "EST", "Australia/Melbourne"},
{-36000, 1, "SAKT", "SAKST", "Asia/Sakhalin"},
{-36000, 1, "VLAT", "VLAST", "Asia/Vladivostok"},
/*{-34200, 1, "CST", "CST", "Australia/Adelaide"},*/
{-34200, 2, "CST", "CST", "Australia/South"},
{-32400, 1, "YAKT", "YAKST", "Asia/Yakutsk"},
{-32400, 1, "CHOT", "CHOST", "Asia/Choibalsan"},
{-31500, 2, "CWST", "CWST", "Australia/Eucla"},
{-28800, 1, "IRKT", "IRKST", "Asia/Irkutsk"},
{-28800, 1, "ULAT", "ULAST", "Asia/Ulaanbaatar"},
{-28800, 2, "WST", "WST", "Australia/West"},
{-25200, 1, "HOVT", "HOVST", "Asia/Hovd"},
{-25200, 1, "KRAT", "KRAST", "Asia/Krasnoyarsk"},
{-21600, 1, "NOVT", "NOVST", "Asia/Novosibirsk"},
@ -672,43 +667,49 @@ static const struct OffsetZoneMapping OFFSET_ZONE_MAPPINGS[] = {
{-14400, 1, "AZT", "AZST", "Asia/Baku"},
{-10800, 1, "AST", "ADT", "Asia/Baghdad"},
{-10800, 1, "MSK", "MSD", "Europe/Moscow"},
{-10800, 1, "VOLT", "VOLST", "Europe/Volgograd"},
{-7200, 0, "EET", "CEST", "Africa/Tripoli"},
/*{-7200, 1, "EET", "EEST", "Africa/Cairo"},*/
/*{-7200, 1, "EET", "EEST", "Egypt"},*/ /* Conflicts with Europe/Tiraspol */
{-7200, 1, "IST", "IDT", "Asia/Jerusalem"},
{-3600, 0, "CET", "WEST", "Africa/Algiers"},
/*{-3600, 1, "WAT", "WAST", "Africa/Windhoek"},*/
{-3600, 2, "WAT", "WAST", "Africa/Windhoek"},
{0, 1, "GMT", "IST", "Europe/Dublin"},
{0, 1, "GMT", "BST", "Europe/London"},
/*{0, 1, "WET", "WEST", "Africa/Casablanca"},*/
{0, 0, "WET", "WEST", "Africa/Casablanca"},
{0, 0, "WET", "WET", "Africa/El_Aaiun"},
{3600, 1, "AZOT", "AZOST", "Atlantic/Azores"},
{3600, 1, "EGT", "EGST", "America/Scoresbysund"},
{10800, 1, "PMST", "PMDT", "America/Miquelon"},
{10800, 1, "UYT", "UYST", "America/Montevideo"},
{10800, 2, "UYT", "UYST", "America/Montevideo"},
{10800, 1, "WGT", "WGST", "America/Godthab"},
{10800, 2, "BRT", "BRST", "Brazil/East"},
{12600, 1, "NST", "NDT", "America/St_Johns"},
/*{14400, 1, "AST", "ADT", "America/Halifax"},*/
{14400, 1, "CLT", "CLST", "America/Santiago"},
{14400, 1, "FKT", "FKST", "Atlantic/Stanley"},
{14400, 1, "PYT", "PYST", "America/Asuncion"},
{18000, 1, "CST", "CDT", "America/Havana"},
/*{18000, 1, "EST", "EDT", "America/New_York"},*/ /* This doesn't work for America/Indianapolis, America/Jamaica, and some other non-US regions. */
{21600, 1, "EAST", "EASST", "Chile/EasterIsland"},
{21600, 0, "CST", "MDT", "America/Regina"},
/*{25200, 1, "MST", "MDT", "America/Denver"},*/ /* This doesn't work for America/Phoenix and some places in Mexico */
{14400, 1, "AST", "ADT", "America/Halifax"},
{14400, 2, "AMT", "AMST", "America/Cuiaba"},
{14400, 2, "CLT", "CLST", "Chile/Continental"},
{14400, 2, "FKT", "FKST", "Atlantic/Stanley"},
{14400, 2, "PYT", "PYST", "America/Asuncion"},
{18000, 1, "CST", "CDT", "Cuba"},
{18000, 1, "EST", "EDT", "US/Eastern"}, /* Conflicts with America/Grand_Turk */
{21600, 2, "EAST", "EASST", "Chile/EasterIsland"},
{21600, 0, "CST", "MDT", "Canada/Saskatchewan"},
{21600, 0, "CST", "CDT", "America/Guatemala"},
{21600, 1, "CST", "CDT", "US/Central"}, /* Conflicts with Mexico/General */
{25200, 1, "MST", "MDT", "US/Mountain"}, /* Conflicts with Mexico/BajaSur */
{28800, 0, "PST", "PST", "Pacific/Pitcairn"},
{28800, 1, "PST", "PDT", "US/Pacific"}, /* Conflicts with America/Ensenada */
{32400, 1, "AKST", "AKDT", "America/Juneau"},
{36000, 1, "HAST", "HADT", "America/Adak"}
};
static const char* remapShortTimeZone(const char *stdID, const char *dstID, int32_t daylightUsed, int32_t offset)
static const char* remapShortTimeZone(const char *stdID, const char *dstID, int32_t daylightType, int32_t offset)
{
int32_t idx;
/*fprintf(stderr, "std=%s dst=%s daylight=%d offset=%d\n", stdID, dstID, daylightUsed, offset);*/
fprintf(stderr, "TZ=%s std=%s dst=%s daylight=%d offset=%d\n", getenv("TZ"), stdID, dstID, daylightType, offset);
for (idx = 0; idx < (int32_t)sizeof(OFFSET_ZONE_MAPPINGS)/sizeof(OFFSET_ZONE_MAPPINGS[0]); idx++)
{
if (offset == OFFSET_ZONE_MAPPINGS[idx].offsetSeconds
&& daylightUsed == OFFSET_ZONE_MAPPINGS[idx].daylightUsed
&& daylightType == OFFSET_ZONE_MAPPINGS[idx].daylightType
&& strcmp(OFFSET_ZONE_MAPPINGS[idx].stdID, stdID) == 0
&& strcmp(OFFSET_ZONE_MAPPINGS[idx].dstID, dstID) == 0)
{
@ -740,6 +741,7 @@ uprv_tzname(int n)
}
#endif*/
#if 1
tzid = getenv("TZ");
if (tzid != NULL && isValidOlsonID(tzid))
{
@ -753,6 +755,7 @@ uprv_tzname(int n)
return tzid;
}
/* else U_TZNAME will give a better result. */
#endif
#if defined(CHECK_LOCALTIME_LINK)
/* Caller must handle threading issues */
@ -786,12 +789,23 @@ uprv_tzname(int n)
So we remap the abbreviation to an olson ID.
Since Windows exposes a little more timezone information,
we normally don't use this code on Windows because uprv_detectWindowsTimeZone
should have already given the correct answer.
we normally don't use this code on Windows because
uprv_detectWindowsTimeZone should have already given the correct answer.
*/
tzid = remapShortTimeZone(U_TZNAME[0], U_TZNAME[1], uprv_daylight(), uprv_timezone());
if (tzid != NULL) {
return tzid;
{
struct tm juneSol, decemberSol;
int daylightType;
static const time_t juneSolstice=1182478260; /*2007-06-21 18:11 UT*/
static const time_t decemberSolstice=1198332540; /*2007-12-22 06:09 UT*/
/* This probing will tell us when daylight savings occurs. */
localtime_r(&juneSolstice, &juneSol);
localtime_r(&decemberSolstice, &decemberSol);
daylightType = ((decemberSol.tm_isdst > 0) << 1) | (juneSol.tm_isdst > 0);
tzid = remapShortTimeZone(U_TZNAME[0], U_TZNAME[1], daylightType, uprv_timezone());
if (tzid != NULL) {
return tzid;
}
}
#endif
return U_TZNAME[n];

View file

@ -266,9 +266,6 @@ typedef unsigned int uint32_t;
#if @U_HAVE_TZNAME@
#define U_TZNAME @U_TZNAME@
#endif
#if @U_HAVE_DAYLIGHT@
#define U_DAYLIGHT @U_DAYLIGHT@
#endif
#define U_HAVE_MMAP @HAVE_MMAP@
#define U_HAVE_POPEN @U_HAVE_POPEN@

View file

@ -52,7 +52,7 @@ THREADSCPPFLAGS = -D_OPEN_THREADS
# For a dynamically called DLL module to share access to the POSIX external
# variables, with its caller, the DLL module must define these _SHR_* macros.
SHAREDLIBCPPFLAGS = -D_SHR_TZNAME -D_SHR_TIMEZONE -D_SHR_DAYLIGHT
SHAREDLIBCPPFLAGS = -D_SHR_TZNAME -D_SHR_TIMEZONE
# -Wc,expo is used to export all functions
SHAREDLIBCFLAGS = -Wc,expo

133
icu4c/source/configure vendored
View file

@ -309,7 +309,7 @@ ac_includes_default="\
# include <unistd.h>
#endif"
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS PACKAGE VERSION LIB_VERSION LIB_VERSION_MAJOR UNICODE_VERSION build build_cpu build_vendor build_os host host_cpu host_vendor host_os CPPFLAGS CC CFLAGS LDFLAGS ac_ct_CC EXEEXT OBJEXT CXX CXXFLAGS ac_ct_CXX INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA U_MAKE DOXYGEN ARFLAGS COMPILE_LINK_ENVVAR LIB_M ENABLE_SHARED ENABLE_STATIC ENABLE_DEBUG ENABLE_RELEASE U_DEFAULT_SHOW_DRAFT U_USE_GCC_VISIBILITY_ATTRIBUTE LIBCFLAGS LIBCXXFLAGS RANLIB ac_ct_RANLIB AR U_DISABLE_RENAMING U_ENABLE_TRACING ENABLE_RPATH U_INLINE THREADS_TRUE ICU_USE_THREADS LIB_THREAD HAVE_MMAP GENCCODE_ASSEMBLY CPP EGREP U_HAVE_INTTYPES_H U_IOSTREAM_SOURCE U_IS_BIG_ENDIAN U_HAVE_NL_LANGINFO_CODESET U_NL_LANGINFO_CODESET U_HAVE_NAMESPACE U_OVERRIDE_CXX_ALLOCATION U_HAVE_PLACEMENT_NEW U_HAVE_POPEN U_HAVE_TZSET U_TZSET U_HAVE_TZNAME U_TZNAME U_HAVE_TIMEZONE U_TIMEZONE U_HAVE_DAYLIGHT U_DAYLIGHT HAVE_INT8_T HAVE_UINT8_T HAVE_INT16_T HAVE_UINT16_T HAVE_INT32_T HAVE_UINT32_T HAVE_INT64_T HAVE_UINT64_T U_HAVE_WCHAR_H U_HAVE_WCSCPY U_SIZEOF_WCHAR_T U_CHECK_UTF16_STRING EXTRAS_TRUE ICUIO_TRUE LAYOUT_TRUE pkgicudatadir thepkgicudatadir DATA_PACKAGING_MODE ICULIBSUFFIX U_HAVE_LIB_SUFFIX ICULIBSUFFIXCNAME TESTS_TRUE SAMPLES_TRUE ICUDATA_CHAR platform platform_make_fragment_name platform_make_fragment LIBOBJS LTLIBOBJS'
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS PACKAGE VERSION LIB_VERSION LIB_VERSION_MAJOR UNICODE_VERSION build build_cpu build_vendor build_os host host_cpu host_vendor host_os CPPFLAGS CC CFLAGS LDFLAGS ac_ct_CC EXEEXT OBJEXT CXX CXXFLAGS ac_ct_CXX INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA U_MAKE DOXYGEN ARFLAGS COMPILE_LINK_ENVVAR LIB_M ENABLE_SHARED ENABLE_STATIC ENABLE_DEBUG ENABLE_RELEASE U_DEFAULT_SHOW_DRAFT U_USE_GCC_VISIBILITY_ATTRIBUTE LIBCFLAGS LIBCXXFLAGS RANLIB ac_ct_RANLIB AR U_DISABLE_RENAMING U_ENABLE_TRACING ENABLE_RPATH U_INLINE THREADS_TRUE ICU_USE_THREADS LIB_THREAD HAVE_MMAP GENCCODE_ASSEMBLY CPP EGREP U_HAVE_INTTYPES_H U_IOSTREAM_SOURCE U_IS_BIG_ENDIAN U_HAVE_NL_LANGINFO_CODESET U_NL_LANGINFO_CODESET U_HAVE_NAMESPACE U_OVERRIDE_CXX_ALLOCATION U_HAVE_PLACEMENT_NEW U_HAVE_POPEN U_HAVE_TZSET U_TZSET U_HAVE_TZNAME U_TZNAME U_HAVE_TIMEZONE U_TIMEZONE HAVE_INT8_T HAVE_UINT8_T HAVE_INT16_T HAVE_UINT16_T HAVE_INT32_T HAVE_UINT32_T HAVE_INT64_T HAVE_UINT64_T U_HAVE_WCHAR_H U_HAVE_WCSCPY U_SIZEOF_WCHAR_T U_CHECK_UTF16_STRING EXTRAS_TRUE ICUIO_TRUE LAYOUT_TRUE pkgicudatadir thepkgicudatadir DATA_PACKAGING_MODE ICULIBSUFFIX U_HAVE_LIB_SUFFIX ICULIBSUFFIXCNAME TESTS_TRUE SAMPLES_TRUE ICUDATA_CHAR platform platform_make_fragment_name platform_make_fragment LIBOBJS LTLIBOBJS'
ac_subst_files=''
# Initialize some variables set by options.
@ -6576,135 +6576,6 @@ fi
U_HAVE_DAYLIGHT=0
echo "$as_me:$LINENO: checking for daylight" >&5
echo $ECHO_N "checking for daylight... $ECHO_C" >&6
if test "${ac_cv_var_daylight+set}" = set; then
echo $ECHO_N "(cached) $ECHO_C" >&6
else
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
#ifndef __USE_POSIX
#define __USE_POSIX
#endif
#ifndef __USE_XOPEN
#define __USE_XOPEN
#endif
#include <stdlib.h>
#include <time.h>
int
main ()
{
daylight = 1;
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext conftest$ac_exeext
if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
(eval $ac_link) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest$ac_exeext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
ac_cv_var_daylight=yes
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
ac_cv_var_daylight=no
fi
rm -f conftest.err conftest.$ac_objext \
conftest$ac_exeext conftest.$ac_ext
fi
echo "$as_me:$LINENO: result: $ac_cv_var_daylight" >&5
echo "${ECHO_T}$ac_cv_var_daylight" >&6
if test $ac_cv_var_daylight = yes; then
U_DAYLIGHT=daylight
U_HAVE_DAYLIGHT=1
else
echo "$as_me:$LINENO: checking for __daylight" >&5
echo $ECHO_N "checking for __daylight... $ECHO_C" >&6
if test "${ac_cv_var___daylight+set}" = set; then
echo $ECHO_N "(cached) $ECHO_C" >&6
else
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
#include <time.h>
int
main ()
{
__daylight = 1;
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext conftest$ac_exeext
if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
(eval $ac_link) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest$ac_exeext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
ac_cv_var___daylight=yes
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
ac_cv_var___daylight=no
fi
rm -f conftest.err conftest.$ac_objext \
conftest$ac_exeext conftest.$ac_ext
fi
echo "$as_me:$LINENO: result: $ac_cv_var___daylight" >&5
echo "${ECHO_T}$ac_cv_var___daylight" >&6
if test $ac_cv_var___daylight = yes; then
U_DAYLIGHT=__daylight
U_HAVE_DAYLIGHT=1
fi
fi
echo "$as_me:$LINENO: checking for int8_t" >&5
echo $ECHO_N "checking for int8_t... $ECHO_C" >&6
if test "${ac_cv_type_int8_t+set}" = set; then
@ -9153,8 +9024,6 @@ s,@U_HAVE_TZNAME@,$U_HAVE_TZNAME,;t t
s,@U_TZNAME@,$U_TZNAME,;t t
s,@U_HAVE_TIMEZONE@,$U_HAVE_TIMEZONE,;t t
s,@U_TIMEZONE@,$U_TIMEZONE,;t t
s,@U_HAVE_DAYLIGHT@,$U_HAVE_DAYLIGHT,;t t
s,@U_DAYLIGHT@,$U_DAYLIGHT,;t t
s,@HAVE_INT8_T@,$HAVE_INT8_T,;t t
s,@HAVE_UINT8_T@,$HAVE_UINT8_T,;t t
s,@HAVE_INT16_T@,$HAVE_INT16_T,;t t

View file

@ -698,36 +698,6 @@ fi
AC_SUBST(U_HAVE_TIMEZONE)
AC_SUBST(U_TIMEZONE)
U_HAVE_DAYLIGHT=0
AC_CACHE_CHECK(for daylight,ac_cv_var_daylight,
[AC_TRY_LINK(
changequote(<<, >>)dnl
<<#ifndef __USE_POSIX
#define __USE_POSIX
#endif
#ifndef __USE_XOPEN
#define __USE_XOPEN
#endif
#include <stdlib.h>
#include <time.h>
>>,
changequote([, ])dnl
[daylight = 1;], ac_cv_var_daylight=yes, ac_cv_var_daylight=no)])
if test $ac_cv_var_daylight = yes; then
U_DAYLIGHT=daylight
U_HAVE_DAYLIGHT=1
else
AC_CACHE_CHECK(for __daylight,ac_cv_var___daylight,
[AC_TRY_LINK([#include <time.h>],
[__daylight = 1;], ac_cv_var___daylight=yes, ac_cv_var___daylight=no)])
if test $ac_cv_var___daylight = yes; then
U_DAYLIGHT=__daylight
U_HAVE_DAYLIGHT=1
fi
fi
AC_SUBST(U_HAVE_DAYLIGHT)
AC_SUBST(U_DAYLIGHT)
dnl Checks for typedefs
AC_CHECK_TYPE(int8_t,signed char)
AC_CHECK_TYPE(uint8_t,unsigned char)