mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 15:24:43 +02:00
8209167: Use CLDR's time zone mappings for Windows
Reviewed-by: erikj, rriggs, ihse
This commit is contained in:
parent
85b57de9ce
commit
009cd15a1b
7 changed files with 176 additions and 289 deletions
|
@ -36,6 +36,7 @@
|
|||
|
||||
#define MAX_ZONE_CHAR 256
|
||||
#define MAX_MAPID_LENGTH 32
|
||||
#define MAX_REGION_LENGTH 4
|
||||
|
||||
#define NT_TZ_KEY "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones"
|
||||
#define WIN_TZ_KEY "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Time Zones"
|
||||
|
@ -145,7 +146,7 @@ static void customZoneName(LONG bias, char *buffer) {
|
|||
/*
|
||||
* Gets the current time zone entry in the "Time Zones" registry.
|
||||
*/
|
||||
static int getWinTimeZone(char *winZoneName, char *winMapID)
|
||||
static int getWinTimeZone(char *winZoneName)
|
||||
{
|
||||
DYNAMIC_TIME_ZONE_INFORMATION dtzi;
|
||||
DWORD timeType;
|
||||
|
@ -231,7 +232,6 @@ static int getWinTimeZone(char *winZoneName, char *winMapID)
|
|||
WCHAR stdNameInReg[MAX_ZONE_CHAR];
|
||||
TziValue tempTzi;
|
||||
WCHAR *stdNamePtr = tzi.StandardName;
|
||||
DWORD valueSize;
|
||||
int onlyMapID;
|
||||
|
||||
timeType = GetTimeZoneInformation(&tzi);
|
||||
|
@ -372,24 +372,7 @@ static int getWinTimeZone(char *winZoneName, char *winMapID)
|
|||
(void) RegCloseKey(hSubKey);
|
||||
}
|
||||
|
||||
/*
|
||||
* Get the "MapID" value of the registry to be able to eliminate
|
||||
* duplicated key names later.
|
||||
*/
|
||||
valueSize = MAX_MAPID_LENGTH;
|
||||
ret = RegQueryValueExA(hSubKey, "MapID", NULL, &valueType, winMapID, &valueSize);
|
||||
(void) RegCloseKey(hSubKey);
|
||||
(void) RegCloseKey(hKey);
|
||||
|
||||
if (ret != ERROR_SUCCESS) {
|
||||
/*
|
||||
* Vista doesn't have mapID. VALUE_UNKNOWN should be returned
|
||||
* only for Windows NT.
|
||||
*/
|
||||
if (onlyMapID == 1) {
|
||||
return VALUE_UNKNOWN;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return VALUE_KEY;
|
||||
|
@ -410,24 +393,17 @@ static int getWinTimeZone(char *winZoneName, char *winMapID)
|
|||
* Index values for the mapping table.
|
||||
*/
|
||||
#define TZ_WIN_NAME 0
|
||||
#define TZ_MAPID 1
|
||||
#define TZ_REGION 2
|
||||
#define TZ_JAVA_NAME 3
|
||||
#define TZ_REGION 1
|
||||
#define TZ_JAVA_NAME 2
|
||||
|
||||
#define TZ_NITEMS 4 /* number of items (fields) */
|
||||
#define TZ_NITEMS 3 /* number of items (fields) */
|
||||
|
||||
/*
|
||||
* Looks up the mapping table (tzmappings) and returns a Java time
|
||||
* zone ID (e.g., "America/Los_Angeles") if found. Otherwise, NULL is
|
||||
* returned.
|
||||
*
|
||||
* value_type is one of the following values:
|
||||
* VALUE_KEY for exact key matching
|
||||
* VALUE_MAPID for MapID (this is
|
||||
* required for the old Windows, such as NT 4.0 SP3).
|
||||
*/
|
||||
static char *matchJavaTZ(const char *java_home_dir, int value_type, char *tzName,
|
||||
char *mapID)
|
||||
static char *matchJavaTZ(const char *java_home_dir, char *tzName)
|
||||
{
|
||||
int line;
|
||||
int IDmatched = 0;
|
||||
|
@ -436,9 +412,22 @@ static char *matchJavaTZ(const char *java_home_dir, int value_type, char *tzName
|
|||
char *items[TZ_NITEMS];
|
||||
char *mapFileName;
|
||||
char lineBuffer[MAX_ZONE_CHAR * 4];
|
||||
int noMapID = *mapID == '\0'; /* no mapID on Vista and later */
|
||||
int offset = 0;
|
||||
const char* errorMessage = "unknown error";
|
||||
char region[MAX_REGION_LENGTH];
|
||||
|
||||
// Get the user's location
|
||||
if (GetGeoInfo(GetUserGeoID(GEOCLASS_NATION),
|
||||
GEO_ISO2, region, MAX_REGION_LENGTH, 0) == 0) {
|
||||
// If GetGeoInfo fails, fallback to LCID's country
|
||||
LCID lcid = GetUserDefaultLCID();
|
||||
if (GetLocaleInfo(lcid,
|
||||
LOCALE_SISO3166CTRYNAME, region, MAX_REGION_LENGTH) == 0 &&
|
||||
GetLocaleInfo(lcid,
|
||||
LOCALE_SISO3166CTRYNAME2, region, MAX_REGION_LENGTH) == 0) {
|
||||
region[0] = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
mapFileName = malloc(strlen(java_home_dir) + strlen(MAPPINGS_FILE) + 1);
|
||||
if (mapFileName == NULL) {
|
||||
|
@ -494,28 +483,20 @@ static char *matchJavaTZ(const char *java_home_dir, int value_type, char *tzName
|
|||
goto illegal_format;
|
||||
}
|
||||
|
||||
if (noMapID || strcmp(mapID, items[TZ_MAPID]) == 0) {
|
||||
/*
|
||||
* We need to scan items until the
|
||||
* exact match is found or the end of data is detected.
|
||||
*/
|
||||
if (strcmp(items[TZ_WIN_NAME], tzName) == 0) {
|
||||
/*
|
||||
* When there's no mapID, we need to scan items until the
|
||||
* exact match is found or the end of data is detected.
|
||||
* Found the time zone in the mapping table.
|
||||
* Check the region code and select the appropriate entry
|
||||
*/
|
||||
if (!noMapID) {
|
||||
IDmatched = 1;
|
||||
}
|
||||
if (strcmp(items[TZ_WIN_NAME], tzName) == 0) {
|
||||
/*
|
||||
* Found the time zone in the mapping table.
|
||||
*/
|
||||
if (strcmp(items[TZ_REGION], region) == 0 ||
|
||||
strcmp(items[TZ_REGION], "001") == 0) {
|
||||
javaTZName = _strdup(items[TZ_JAVA_NAME]);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
if (IDmatched == 1) {
|
||||
/*
|
||||
* No need to look up the mapping table further.
|
||||
*/
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
fclose(fp);
|
||||
|
@ -535,19 +516,16 @@ static char *matchJavaTZ(const char *java_home_dir, int value_type, char *tzName
|
|||
char *findJavaTZ_md(const char *java_home_dir)
|
||||
{
|
||||
char winZoneName[MAX_ZONE_CHAR];
|
||||
char winMapID[MAX_MAPID_LENGTH];
|
||||
char *std_timezone = NULL;
|
||||
int result;
|
||||
|
||||
winMapID[0] = 0;
|
||||
result = getWinTimeZone(winZoneName, winMapID);
|
||||
result = getWinTimeZone(winZoneName);
|
||||
|
||||
if (result != VALUE_UNKNOWN) {
|
||||
if (result == VALUE_GMTOFFSET) {
|
||||
std_timezone = _strdup(winZoneName);
|
||||
} else {
|
||||
std_timezone = matchJavaTZ(java_home_dir, result,
|
||||
winZoneName, winMapID);
|
||||
std_timezone = matchJavaTZ(java_home_dir, winZoneName);
|
||||
if (std_timezone == NULL) {
|
||||
std_timezone = getGMTOffsetID();
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue