mirror of
https://github.com/reactos/reactos.git
synced 2024-12-27 09:34:43 +00:00
[TIMEDATE.CPL][SYSSETUP][TZLIB] Introduce a small static library "tzlib": "TimeZone Utilities Library", and use it in timedate.cpl and syssetup.dll.
This small win32 library provides time-zone utility wrappers around Win32 functions, that are used by different ReactOS modules such as timedate.cpl, syssetup.dll, and a possible future 'tzutil' tool. The code has been extracted from the common code found in both timedate.cpl and syssetup.dll.
This commit is contained in:
parent
87f6c82d85
commit
7c3e96a26a
9 changed files with 605 additions and 539 deletions
|
@ -1,4 +1,6 @@
|
|||
|
||||
include_directories(${REACTOS_SOURCE_DIR}/sdk/lib/tzlib)
|
||||
|
||||
spec2def(timedate.cpl timedate.spec)
|
||||
|
||||
list(APPEND SOURCE
|
||||
|
@ -19,6 +21,7 @@ add_library(timedate MODULE
|
|||
${CMAKE_CURRENT_BINARY_DIR}/timedate.def)
|
||||
|
||||
set_module_type(timedate cpl UNICODE)
|
||||
target_link_libraries(timedate tzlib)
|
||||
add_importlibs(timedate w32time advapi32 user32 gdi32 comctl32 ws2_32 iphlpapi msvcrt kernel32 ntdll)
|
||||
add_pch(timedate timedate.h SOURCE)
|
||||
add_cd_file(TARGET timedate DESTINATION reactos/system32 FOR all)
|
||||
|
|
|
@ -10,25 +10,16 @@
|
|||
*/
|
||||
|
||||
#include "timedate.h"
|
||||
|
||||
// See also sdk/include/reactos/libs/syssetup/syssetup.h
|
||||
typedef struct _TZ_INFO
|
||||
{
|
||||
LONG Bias;
|
||||
LONG StandardBias;
|
||||
LONG DaylightBias;
|
||||
SYSTEMTIME StandardDate;
|
||||
SYSTEMTIME DaylightDate;
|
||||
} TZ_INFO, *PTZ_INFO;
|
||||
#include <tzlib.h>
|
||||
|
||||
typedef struct _TIMEZONE_ENTRY
|
||||
{
|
||||
struct _TIMEZONE_ENTRY *Prev;
|
||||
struct _TIMEZONE_ENTRY *Next;
|
||||
WCHAR Description[128]; /* 'Display' */
|
||||
WCHAR StandardName[33]; /* 'Std' */
|
||||
WCHAR DaylightName[33]; /* 'Dlt' */
|
||||
TZ_INFO TimezoneInfo; /* 'TZI' */
|
||||
WCHAR Description[128]; /* 'Display' */
|
||||
WCHAR StandardName[33]; /* 'Std' */
|
||||
WCHAR DaylightName[33]; /* 'Dlt' */
|
||||
REG_TZI_FORMAT TimezoneInfo; /* 'TZI' */
|
||||
} TIMEZONE_ENTRY, *PTIMEZONE_ENTRY;
|
||||
|
||||
|
||||
|
@ -64,160 +55,92 @@ GetLargerTimeZoneEntry(
|
|||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
static
|
||||
LONG
|
||||
QueryTimezoneData(
|
||||
HKEY hZoneKey,
|
||||
PTIMEZONE_ENTRY Entry)
|
||||
static LONG
|
||||
RetrieveTimeZone(
|
||||
IN HKEY hZoneKey,
|
||||
IN PVOID Context)
|
||||
{
|
||||
DWORD dwValueSize;
|
||||
LONG lError;
|
||||
PTIMEZONE_ENTRY Entry;
|
||||
PTIMEZONE_ENTRY Current;
|
||||
ULONG DescriptionSize;
|
||||
ULONG StandardNameSize;
|
||||
ULONG DaylightNameSize;
|
||||
|
||||
dwValueSize = sizeof(Entry->Description);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Display",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->Description,
|
||||
&dwValueSize);
|
||||
Entry = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(TIMEZONE_ENTRY));
|
||||
if (Entry == NULL)
|
||||
{
|
||||
return ERROR_NOT_ENOUGH_MEMORY;
|
||||
}
|
||||
|
||||
DescriptionSize = sizeof(Entry->Description);
|
||||
StandardNameSize = sizeof(Entry->StandardName);
|
||||
DaylightNameSize = sizeof(Entry->DaylightName);
|
||||
|
||||
lError = QueryTimeZoneData(hZoneKey,
|
||||
NULL,
|
||||
&Entry->TimezoneInfo,
|
||||
Entry->Description,
|
||||
&DescriptionSize,
|
||||
Entry->StandardName,
|
||||
&StandardNameSize,
|
||||
Entry->DaylightName,
|
||||
&DaylightNameSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, Entry);
|
||||
return lError;
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(Entry->StandardName);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Std",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->StandardName,
|
||||
&dwValueSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
if (TimeZoneListHead == NULL &&
|
||||
TimeZoneListTail == NULL)
|
||||
{
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = NULL;
|
||||
TimeZoneListHead = Entry;
|
||||
TimeZoneListTail = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
Current = GetLargerTimeZoneEntry(Entry->TimezoneInfo.Bias, Entry->Description);
|
||||
if (Current != NULL)
|
||||
{
|
||||
if (Current == TimeZoneListHead)
|
||||
{
|
||||
/* Prepend to head */
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = TimeZoneListHead;
|
||||
TimeZoneListHead->Prev = Entry;
|
||||
TimeZoneListHead = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Insert before current */
|
||||
Entry->Prev = Current->Prev;
|
||||
Entry->Next = Current;
|
||||
Current->Prev->Next = Entry;
|
||||
Current->Prev = Entry;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Append to tail */
|
||||
Entry->Prev = TimeZoneListTail;
|
||||
Entry->Next = NULL;
|
||||
TimeZoneListTail->Next = Entry;
|
||||
TimeZoneListTail = Entry;
|
||||
}
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(Entry->DaylightName);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Dlt",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->DaylightName,
|
||||
&dwValueSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
|
||||
dwValueSize = sizeof(Entry->TimezoneInfo);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"TZI",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->TimezoneInfo,
|
||||
&dwValueSize);
|
||||
return lError;
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static VOID
|
||||
CreateTimeZoneList(VOID)
|
||||
{
|
||||
WCHAR szKeyName[256];
|
||||
DWORD dwIndex;
|
||||
DWORD dwNameSize;
|
||||
LONG lError;
|
||||
HKEY hZonesKey;
|
||||
HKEY hZoneKey;
|
||||
PTIMEZONE_ENTRY Entry;
|
||||
PTIMEZONE_ENTRY Current;
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones",
|
||||
0,
|
||||
KEY_ENUMERATE_SUB_KEYS,
|
||||
&hZonesKey))
|
||||
return;
|
||||
|
||||
for (dwIndex = 0; ; dwIndex++)
|
||||
{
|
||||
dwNameSize = sizeof(szKeyName);
|
||||
lError = RegEnumKeyExW(hZonesKey,
|
||||
dwIndex,
|
||||
szKeyName,
|
||||
&dwNameSize,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL);
|
||||
if (lError == ERROR_NO_MORE_ITEMS)
|
||||
break;
|
||||
|
||||
if (RegOpenKeyEx (hZonesKey,
|
||||
szKeyName,
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hZoneKey))
|
||||
break;
|
||||
|
||||
Entry = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(TIMEZONE_ENTRY));
|
||||
if (Entry == NULL)
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
lError = QueryTimezoneData(hZoneKey,
|
||||
Entry);
|
||||
|
||||
RegCloseKey(hZoneKey);
|
||||
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, Entry);
|
||||
break;
|
||||
}
|
||||
|
||||
if (TimeZoneListHead == NULL &&
|
||||
TimeZoneListTail == NULL)
|
||||
{
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = NULL;
|
||||
TimeZoneListHead = Entry;
|
||||
TimeZoneListTail = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
Current = GetLargerTimeZoneEntry(Entry->TimezoneInfo.Bias, Entry->Description);
|
||||
if (Current != NULL)
|
||||
{
|
||||
if (Current == TimeZoneListHead)
|
||||
{
|
||||
/* Prepend to head */
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = TimeZoneListHead;
|
||||
TimeZoneListHead->Prev = Entry;
|
||||
TimeZoneListHead = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Insert before current */
|
||||
Entry->Prev = Current->Prev;
|
||||
Entry->Next = Current;
|
||||
Current->Prev->Next = Entry;
|
||||
Current->Prev = Entry;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Append to tail */
|
||||
Entry->Prev = TimeZoneListTail;
|
||||
Entry->Next = NULL;
|
||||
TimeZoneListTail->Next = Entry;
|
||||
TimeZoneListTail = Entry;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RegCloseKey(hZonesKey);
|
||||
EnumerateTimeZoneList(RetrieveTimeZone, NULL);
|
||||
}
|
||||
|
||||
|
||||
static VOID
|
||||
DestroyTimeZoneList(VOID)
|
||||
{
|
||||
|
@ -299,9 +222,9 @@ SetLocalTimeZone(HWND hwnd)
|
|||
}
|
||||
|
||||
wcscpy(TimeZoneInformation.StandardName,
|
||||
Entry->StandardName);
|
||||
Entry->StandardName);
|
||||
wcscpy(TimeZoneInformation.DaylightName,
|
||||
Entry->DaylightName);
|
||||
Entry->DaylightName);
|
||||
|
||||
TimeZoneInformation.Bias = Entry->TimezoneInfo.Bias;
|
||||
TimeZoneInformation.StandardBias = Entry->TimezoneInfo.StandardBias;
|
||||
|
@ -319,71 +242,6 @@ SetLocalTimeZone(HWND hwnd)
|
|||
}
|
||||
|
||||
|
||||
static VOID
|
||||
GetAutoDaylightInfo(HWND hwnd)
|
||||
{
|
||||
HKEY hKey;
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\TimeZoneInformation",
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hKey))
|
||||
return;
|
||||
|
||||
/* If the call fails (non zero), the reg value isn't available,
|
||||
* which means it shouldn't be disabled, so we should check the button.
|
||||
*/
|
||||
if (RegQueryValueExW(hKey,
|
||||
L"DisableAutoDaylightTimeSet",
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL))
|
||||
{
|
||||
SendMessageW(hwnd, BM_SETCHECK, (WPARAM)BST_CHECKED, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
SendMessageW(hwnd, BM_SETCHECK, (WPARAM)BST_UNCHECKED, 0);
|
||||
}
|
||||
|
||||
RegCloseKey(hKey);
|
||||
}
|
||||
|
||||
|
||||
static VOID
|
||||
SetAutoDaylightInfo(HWND hwnd)
|
||||
{
|
||||
HKEY hKey;
|
||||
DWORD dwValue = 1;
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\TimeZoneInformation",
|
||||
0,
|
||||
KEY_SET_VALUE,
|
||||
&hKey))
|
||||
return;
|
||||
|
||||
if (SendMessageW(hwnd, BM_GETCHECK, 0, 0) == BST_UNCHECKED)
|
||||
{
|
||||
RegSetValueExW(hKey,
|
||||
L"DisableAutoDaylightTimeSet",
|
||||
0,
|
||||
REG_DWORD,
|
||||
(LPBYTE)&dwValue,
|
||||
sizeof(dwValue));
|
||||
}
|
||||
else
|
||||
{
|
||||
RegDeleteValueW(hKey,
|
||||
L"DisableAutoDaylightTimeSet");
|
||||
}
|
||||
|
||||
RegCloseKey(hKey);
|
||||
}
|
||||
|
||||
|
||||
/* Property page dialog callback */
|
||||
INT_PTR CALLBACK
|
||||
TimeZonePageProc(HWND hwndDlg,
|
||||
|
@ -396,9 +254,13 @@ TimeZonePageProc(HWND hwndDlg,
|
|||
switch (uMsg)
|
||||
{
|
||||
case WM_INITDIALOG:
|
||||
{
|
||||
CreateTimeZoneList();
|
||||
ShowTimeZoneList(GetDlgItem(hwndDlg, IDC_TIMEZONELIST));
|
||||
GetAutoDaylightInfo(GetDlgItem(hwndDlg, IDC_AUTODAYLIGHT));
|
||||
|
||||
SendDlgItemMessage(hwndDlg, IDC_AUTODAYLIGHT, BM_SETCHECK,
|
||||
(WPARAM)(GetAutoDaylight() ? BST_CHECKED : BST_UNCHECKED), 0);
|
||||
|
||||
hBitmap = LoadImageW(hApplet, MAKEINTRESOURCEW(IDC_WORLD), IMAGE_BITMAP, 0, 0, LR_DEFAULTCOLOR);
|
||||
if (hBitmap != NULL)
|
||||
{
|
||||
|
@ -408,6 +270,7 @@ TimeZonePageProc(HWND hwndDlg,
|
|||
cySource = bitmap.bmHeight;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case WM_DRAWITEM:
|
||||
{
|
||||
|
@ -452,7 +315,8 @@ TimeZonePageProc(HWND hwndDlg,
|
|||
{
|
||||
case PSN_APPLY:
|
||||
{
|
||||
SetAutoDaylightInfo(GetDlgItem(hwndDlg, IDC_AUTODAYLIGHT));
|
||||
SetAutoDaylight(SendDlgItemMessage(hwndDlg, IDC_AUTODAYLIGHT,
|
||||
BM_GETCHECK, 0, 0) != BST_UNCHECKED);
|
||||
SetLocalTimeZone(GetDlgItem(hwndDlg, IDC_TIMEZONELIST));
|
||||
SetWindowLongPtr(hwndDlg, DWLP_MSGRESULT, PSNRET_NOERROR);
|
||||
return TRUE;
|
||||
|
|
|
@ -1,4 +1,6 @@
|
|||
|
||||
include_directories(${REACTOS_SOURCE_DIR}/sdk/lib/tzlib)
|
||||
|
||||
spec2def(syssetup.dll syssetup.spec)
|
||||
|
||||
list(APPEND SOURCE
|
||||
|
@ -20,6 +22,6 @@ add_library(syssetup MODULE
|
|||
|
||||
add_pch(syssetup precomp.h SOURCE)
|
||||
set_module_type(syssetup win32dll UNICODE)
|
||||
target_link_libraries(syssetup uuid wine ${PSEH_LIB})
|
||||
target_link_libraries(syssetup uuid wine tzlib ${PSEH_LIB})
|
||||
add_importlibs(syssetup advapi32 gdi32 user32 samlib userenv comctl32 setupapi rpcrt4 ole32 shell32 shlwapi msvcrt kernel32 ntdll)
|
||||
add_cd_file(TARGET syssetup DESTINATION reactos/system32 FOR all)
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
#include <wincon.h>
|
||||
#include <shlobj.h>
|
||||
|
||||
#include <tzlib.h>
|
||||
|
||||
#define NDEBUG
|
||||
#include <debug.h>
|
||||
|
||||
|
@ -45,6 +47,17 @@ typedef struct _REGISTRATIONDATA
|
|||
PVOID DefaultContext;
|
||||
} REGISTRATIONDATA, *PREGISTRATIONDATA;
|
||||
|
||||
typedef struct _TIMEZONE_ENTRY
|
||||
{
|
||||
struct _TIMEZONE_ENTRY *Prev;
|
||||
struct _TIMEZONE_ENTRY *Next;
|
||||
WCHAR Description[128]; /* 'Display' */
|
||||
WCHAR StandardName[32]; /* 'Std' */
|
||||
WCHAR DaylightName[32]; /* 'Dlt' */
|
||||
REG_TZI_FORMAT TimezoneInfo; /* 'TZI' */
|
||||
ULONG Index;
|
||||
} TIMEZONE_ENTRY, *PTIMEZONE_ENTRY;
|
||||
|
||||
|
||||
/* FUNCTIONS ****************************************************************/
|
||||
|
||||
|
@ -1237,166 +1250,93 @@ GetLargerTimeZoneEntry(PSETUPDATA SetupData, DWORD Index)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static LONG
|
||||
RetrieveTimeZone(
|
||||
IN HKEY hZoneKey,
|
||||
IN PVOID Context)
|
||||
{
|
||||
LONG lError;
|
||||
PSETUPDATA SetupData = (PSETUPDATA)Context;
|
||||
PTIMEZONE_ENTRY Entry;
|
||||
PTIMEZONE_ENTRY Current;
|
||||
ULONG DescriptionSize;
|
||||
ULONG StandardNameSize;
|
||||
ULONG DaylightNameSize;
|
||||
|
||||
Entry = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(TIMEZONE_ENTRY));
|
||||
if (Entry == NULL)
|
||||
{
|
||||
return ERROR_NOT_ENOUGH_MEMORY;
|
||||
}
|
||||
|
||||
DescriptionSize = sizeof(Entry->Description);
|
||||
StandardNameSize = sizeof(Entry->StandardName);
|
||||
DaylightNameSize = sizeof(Entry->DaylightName);
|
||||
|
||||
lError = QueryTimeZoneData(hZoneKey,
|
||||
&Entry->Index,
|
||||
&Entry->TimezoneInfo,
|
||||
Entry->Description,
|
||||
&DescriptionSize,
|
||||
Entry->StandardName,
|
||||
&StandardNameSize,
|
||||
Entry->DaylightName,
|
||||
&DaylightNameSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, Entry);
|
||||
return lError;
|
||||
}
|
||||
|
||||
if (SetupData->TimeZoneListHead == NULL &&
|
||||
SetupData->TimeZoneListTail == NULL)
|
||||
{
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = NULL;
|
||||
SetupData->TimeZoneListHead = Entry;
|
||||
SetupData->TimeZoneListTail = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
Current = GetLargerTimeZoneEntry(SetupData, Entry->Index);
|
||||
if (Current != NULL)
|
||||
{
|
||||
if (Current == SetupData->TimeZoneListHead)
|
||||
{
|
||||
/* Prepend to head */
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = SetupData->TimeZoneListHead;
|
||||
SetupData->TimeZoneListHead->Prev = Entry;
|
||||
SetupData->TimeZoneListHead = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Insert before current */
|
||||
Entry->Prev = Current->Prev;
|
||||
Entry->Next = Current;
|
||||
Current->Prev->Next = Entry;
|
||||
Current->Prev = Entry;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Append to tail */
|
||||
Entry->Prev = SetupData->TimeZoneListTail;
|
||||
Entry->Next = NULL;
|
||||
SetupData->TimeZoneListTail->Next = Entry;
|
||||
SetupData->TimeZoneListTail = Entry;
|
||||
}
|
||||
}
|
||||
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
|
||||
static VOID
|
||||
CreateTimeZoneList(PSETUPDATA SetupData)
|
||||
{
|
||||
WCHAR szKeyName[256];
|
||||
DWORD dwIndex;
|
||||
DWORD dwNameSize;
|
||||
DWORD dwValueSize;
|
||||
LONG lError;
|
||||
HKEY hZonesKey;
|
||||
HKEY hZoneKey;
|
||||
|
||||
PTIMEZONE_ENTRY Entry;
|
||||
PTIMEZONE_ENTRY Current;
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones",
|
||||
0,
|
||||
KEY_ALL_ACCESS,
|
||||
&hZonesKey))
|
||||
return;
|
||||
|
||||
dwIndex = 0;
|
||||
while (TRUE)
|
||||
{
|
||||
dwNameSize = 256 * sizeof(WCHAR);
|
||||
lError = RegEnumKeyExW(hZonesKey,
|
||||
dwIndex,
|
||||
szKeyName,
|
||||
&dwNameSize,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL);
|
||||
if (lError != ERROR_SUCCESS && lError != ERROR_MORE_DATA)
|
||||
break;
|
||||
|
||||
if (RegOpenKeyExW(hZonesKey,
|
||||
szKeyName,
|
||||
0,
|
||||
KEY_ALL_ACCESS,
|
||||
&hZoneKey))
|
||||
break;
|
||||
|
||||
Entry = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(TIMEZONE_ENTRY));
|
||||
if (Entry == NULL)
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
dwValueSize = 64 * sizeof(WCHAR);
|
||||
if (RegQueryValueExW(hZoneKey,
|
||||
L"Display",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->Description,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
dwValueSize = 32 * sizeof(WCHAR);
|
||||
if (RegQueryValueExW(hZoneKey,
|
||||
L"Std",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->StandardName,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
dwValueSize = 32 * sizeof(WCHAR);
|
||||
if (RegQueryValueExW(hZoneKey,
|
||||
L"Dlt",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->DaylightName,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(DWORD);
|
||||
if (RegQueryValueExW(hZoneKey,
|
||||
L"Index",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->Index,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(TZ_INFO);
|
||||
if (RegQueryValueExW(hZoneKey,
|
||||
L"TZI",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)&Entry->TimezoneInfo,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hZoneKey);
|
||||
break;
|
||||
}
|
||||
|
||||
RegCloseKey(hZoneKey);
|
||||
|
||||
if (SetupData->TimeZoneListHead == NULL &&
|
||||
SetupData->TimeZoneListTail == NULL)
|
||||
{
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = NULL;
|
||||
SetupData->TimeZoneListHead = Entry;
|
||||
SetupData->TimeZoneListTail = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
Current = GetLargerTimeZoneEntry(SetupData, Entry->Index);
|
||||
if (Current != NULL)
|
||||
{
|
||||
if (Current == SetupData->TimeZoneListHead)
|
||||
{
|
||||
/* Prepend to head */
|
||||
Entry->Prev = NULL;
|
||||
Entry->Next = SetupData->TimeZoneListHead;
|
||||
SetupData->TimeZoneListHead->Prev = Entry;
|
||||
SetupData->TimeZoneListHead = Entry;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Insert before current */
|
||||
Entry->Prev = Current->Prev;
|
||||
Entry->Next = Current;
|
||||
Current->Prev->Next = Entry;
|
||||
Current->Prev = Entry;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Append to tail */
|
||||
Entry->Prev = SetupData->TimeZoneListTail;
|
||||
Entry->Next = NULL;
|
||||
SetupData->TimeZoneListTail->Next = Entry;
|
||||
SetupData->TimeZoneListTail = Entry;
|
||||
}
|
||||
}
|
||||
|
||||
dwIndex++;
|
||||
}
|
||||
|
||||
RegCloseKey(hZonesKey);
|
||||
EnumerateTimeZoneList(RetrieveTimeZone, SetupData);
|
||||
}
|
||||
|
||||
|
||||
static VOID
|
||||
DestroyTimeZoneList(PSETUPDATA SetupData)
|
||||
{
|
||||
|
@ -1418,117 +1358,6 @@ DestroyTimeZoneList(PSETUPDATA SetupData)
|
|||
SetupData->TimeZoneListTail = NULL;
|
||||
}
|
||||
|
||||
static BOOL
|
||||
GetTimeZoneListIndex(LPDWORD lpIndex)
|
||||
{
|
||||
WCHAR szLanguageIdString[9];
|
||||
HKEY hKey;
|
||||
DWORD dwValueSize;
|
||||
DWORD Length;
|
||||
LPWSTR Buffer;
|
||||
LPWSTR Ptr;
|
||||
LPWSTR End;
|
||||
BOOL bFound = FALSE;
|
||||
unsigned long iLanguageID;
|
||||
|
||||
if (*lpIndex == -1)
|
||||
{
|
||||
*lpIndex = 85; /* fallback to GMT time zone */
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\NLS\\Language",
|
||||
0,
|
||||
KEY_ALL_ACCESS,
|
||||
&hKey))
|
||||
return FALSE;
|
||||
|
||||
dwValueSize = 9 * sizeof(WCHAR);
|
||||
if (RegQueryValueExW(hKey,
|
||||
L"Default",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)szLanguageIdString,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
iLanguageID = wcstoul(szLanguageIdString, NULL, 16);
|
||||
RegCloseKey(hKey);
|
||||
}
|
||||
else
|
||||
{
|
||||
iLanguageID = *lpIndex;
|
||||
}
|
||||
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones",
|
||||
0,
|
||||
KEY_ALL_ACCESS,
|
||||
&hKey))
|
||||
return FALSE;
|
||||
|
||||
dwValueSize = 0;
|
||||
if (RegQueryValueExW(hKey,
|
||||
L"IndexMapping",
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
&dwValueSize))
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Buffer = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, dwValueSize);
|
||||
if (Buffer == NULL)
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (RegQueryValueExW(hKey,
|
||||
L"IndexMapping",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)Buffer,
|
||||
&dwValueSize))
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
RegCloseKey(hKey);
|
||||
|
||||
Ptr = Buffer;
|
||||
while (*Ptr != 0)
|
||||
{
|
||||
Length = wcslen(Ptr);
|
||||
if (wcstoul(Ptr, NULL, 16) == iLanguageID)
|
||||
bFound = TRUE;
|
||||
|
||||
Ptr = Ptr + Length + 1;
|
||||
if (*Ptr == 0)
|
||||
break;
|
||||
|
||||
if (bFound)
|
||||
{
|
||||
*lpIndex = wcstoul(Ptr, &End, 10);
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
Length = wcslen(Ptr);
|
||||
Ptr = Ptr + Length + 1;
|
||||
}
|
||||
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
static VOID
|
||||
ShowTimeZoneList(HWND hwnd, PSETUPDATA SetupData, DWORD dwEntryIndex)
|
||||
|
@ -1634,32 +1463,6 @@ GetLocalSystemTime(HWND hwnd, PSETUPDATA SetupData)
|
|||
}
|
||||
|
||||
|
||||
static VOID
|
||||
SetAutoDaylightInfo(HWND hwnd)
|
||||
{
|
||||
HKEY hKey;
|
||||
DWORD dwValue = 1;
|
||||
|
||||
if (SendMessage(hwnd, BM_GETCHECK, 0, 0) == BST_UNCHECKED)
|
||||
{
|
||||
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\TimeZoneInformation",
|
||||
0,
|
||||
KEY_SET_VALUE,
|
||||
&hKey))
|
||||
return;
|
||||
|
||||
RegSetValueExW(hKey,
|
||||
L"DisableAutoDaylightTimeSet",
|
||||
0,
|
||||
REG_DWORD,
|
||||
(LPBYTE)&dwValue,
|
||||
sizeof(DWORD));
|
||||
RegCloseKey(hKey);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static BOOL
|
||||
SetSystemLocalTime(HWND hwnd, PSETUPDATA SetupData)
|
||||
{
|
||||
|
@ -1696,7 +1499,8 @@ WriteDateTimeSettings(HWND hwndDlg, PSETUPDATA SetupData)
|
|||
SetLocalTimeZone(GetDlgItem(hwndDlg, IDC_TIMEZONELIST),
|
||||
SetupData);
|
||||
|
||||
SetAutoDaylightInfo(GetDlgItem(hwndDlg, IDC_AUTODAYLIGHT));
|
||||
SetAutoDaylight(SendDlgItemMessage(hwndDlg, IDC_AUTODAYLIGHT,
|
||||
BM_GETCHECK, 0, 0) != BST_UNCHECKED);
|
||||
if (!SetSystemLocalTime(hwndDlg, SetupData))
|
||||
{
|
||||
if (0 == LoadStringW(hDllInstance, IDS_REACTOS_SETUP, Title, ARRAYSIZE(Title)))
|
||||
|
@ -1730,6 +1534,7 @@ DateTimePageDlgProc(HWND hwndDlg,
|
|||
switch (uMsg)
|
||||
{
|
||||
case WM_INITDIALOG:
|
||||
{
|
||||
/* Save pointer to the global setup data */
|
||||
SetupData = (PSETUPDATA)((LPPROPSHEETPAGE)lParam)->lParam;
|
||||
SetWindowLongPtr(hwndDlg, GWLP_USERDATA, (DWORD_PTR)SetupData);
|
||||
|
@ -1754,6 +1559,7 @@ DateTimePageDlgProc(HWND hwndDlg,
|
|||
SendDlgItemMessage(hwndDlg, IDC_AUTODAYLIGHT, BM_SETCHECK, (WPARAM)BST_CHECKED, 0);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case WM_TIMER:
|
||||
UpdateLocalSystemTime(hwndDlg);
|
||||
|
|
|
@ -23,27 +23,6 @@
|
|||
#ifndef __SYSSETUP_H_INCLUDED__
|
||||
#define __SYSSETUP_H_INCLUDED__
|
||||
|
||||
// See also dll/cpl/timedate/timezone.c
|
||||
typedef struct _TZ_INFO
|
||||
{
|
||||
LONG Bias;
|
||||
LONG StandardBias;
|
||||
LONG DaylightBias;
|
||||
SYSTEMTIME StandardDate;
|
||||
SYSTEMTIME DaylightDate;
|
||||
} TZ_INFO, *PTZ_INFO;
|
||||
|
||||
typedef struct _TIMEZONE_ENTRY
|
||||
{
|
||||
struct _TIMEZONE_ENTRY *Prev;
|
||||
struct _TIMEZONE_ENTRY *Next;
|
||||
WCHAR Description[64]; /* 'Display' */
|
||||
WCHAR StandardName[32]; /* 'Std' */
|
||||
WCHAR DaylightName[32]; /* 'Dlt' */
|
||||
TZ_INFO TimezoneInfo; /* 'TZI' */
|
||||
ULONG Index;
|
||||
} TIMEZONE_ENTRY, *PTIMEZONE_ENTRY;
|
||||
|
||||
typedef enum _PRODUCT_OPTION
|
||||
{
|
||||
PRODUCT_OPTION_SERVER,
|
||||
|
@ -67,8 +46,8 @@ typedef struct _SETUPDATA
|
|||
BOOL DisableGeckoInst;
|
||||
|
||||
SYSTEMTIME SystemTime;
|
||||
PTIMEZONE_ENTRY TimeZoneListHead;
|
||||
PTIMEZONE_ENTRY TimeZoneListTail;
|
||||
struct _TIMEZONE_ENTRY* TimeZoneListHead;
|
||||
struct _TIMEZONE_ENTRY* TimeZoneListTail;
|
||||
DWORD TimeZoneIndex;
|
||||
DWORD DisableAutoDaylightTimeSet;
|
||||
LCID LocaleID;
|
||||
|
|
|
@ -46,6 +46,7 @@ add_subdirectory(skiplist)
|
|||
add_subdirectory(strmiids)
|
||||
add_subdirectory(smlib)
|
||||
add_subdirectory(tdilib)
|
||||
add_subdirectory(tzlib)
|
||||
add_subdirectory(udmihelp)
|
||||
add_subdirectory(uuid)
|
||||
add_subdirectory(wdmguid)
|
||||
|
|
3
sdk/lib/tzlib/CMakeLists.txt
Normal file
3
sdk/lib/tzlib/CMakeLists.txt
Normal file
|
@ -0,0 +1,3 @@
|
|||
|
||||
add_library(tzlib tzlib.c)
|
||||
add_dependencies(tzlib xdk)
|
352
sdk/lib/tzlib/tzlib.c
Normal file
352
sdk/lib/tzlib/tzlib.c
Normal file
|
@ -0,0 +1,352 @@
|
|||
/*
|
||||
* PROJECT: ReactOS TimeZone Utilities Library
|
||||
* LICENSE: GPL-2.0 (https://spdx.org/licenses/GPL-2.0)
|
||||
* PURPOSE: Provides time-zone utility wrappers around Win32 functions,
|
||||
* that are used by different ReactOS modules such as
|
||||
* timedate.cpl, syssetup.dll.
|
||||
* COPYRIGHT: Copyright 2004-2005 Eric Kohl
|
||||
* Copyright 2016 Carlo Bramini
|
||||
* Copyright 2020 Hermes Belusca-Maito
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <windef.h>
|
||||
#include <winbase.h>
|
||||
#include <winreg.h>
|
||||
|
||||
#include "tzlib.h"
|
||||
|
||||
BOOL
|
||||
GetTimeZoneListIndex(
|
||||
IN OUT PULONG pIndex)
|
||||
{
|
||||
LONG lError;
|
||||
HKEY hKey;
|
||||
DWORD dwType;
|
||||
DWORD dwValueSize;
|
||||
DWORD Length;
|
||||
LPWSTR Buffer;
|
||||
LPWSTR Ptr, End;
|
||||
BOOL bFound = FALSE;
|
||||
unsigned long iLanguageID;
|
||||
WCHAR szLanguageIdString[9];
|
||||
|
||||
if (*pIndex == -1)
|
||||
{
|
||||
*pIndex = 85; /* fallback to GMT time zone */
|
||||
|
||||
lError = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\NLS\\Language",
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hKey);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(szLanguageIdString);
|
||||
lError = RegQueryValueExW(hKey,
|
||||
L"Default",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)szLanguageIdString,
|
||||
&dwValueSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
iLanguageID = wcstoul(szLanguageIdString, NULL, 16);
|
||||
RegCloseKey(hKey);
|
||||
}
|
||||
else
|
||||
{
|
||||
iLanguageID = *pIndex;
|
||||
}
|
||||
|
||||
lError = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones",
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hKey);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
dwValueSize = 0;
|
||||
lError = RegQueryValueExW(hKey,
|
||||
L"IndexMapping",
|
||||
NULL,
|
||||
&dwType,
|
||||
NULL,
|
||||
&dwValueSize);
|
||||
if ((lError != ERROR_SUCCESS) || (dwType != REG_MULTI_SZ))
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Buffer = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, dwValueSize);
|
||||
if (Buffer == NULL)
|
||||
{
|
||||
RegCloseKey(hKey);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
lError = RegQueryValueExW(hKey,
|
||||
L"IndexMapping",
|
||||
NULL,
|
||||
&dwType,
|
||||
(LPBYTE)Buffer,
|
||||
&dwValueSize);
|
||||
|
||||
RegCloseKey(hKey);
|
||||
|
||||
if ((lError != ERROR_SUCCESS) || (dwType != REG_MULTI_SZ))
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Ptr = Buffer;
|
||||
while (*Ptr != 0)
|
||||
{
|
||||
Length = wcslen(Ptr);
|
||||
if (wcstoul(Ptr, NULL, 16) == iLanguageID)
|
||||
bFound = TRUE;
|
||||
|
||||
Ptr = Ptr + Length + 1;
|
||||
if (*Ptr == 0)
|
||||
break;
|
||||
|
||||
if (bFound)
|
||||
{
|
||||
*pIndex = wcstoul(Ptr, &End, 10);
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
Length = wcslen(Ptr);
|
||||
Ptr = Ptr + Length + 1;
|
||||
}
|
||||
|
||||
HeapFree(GetProcessHeap(), 0, Buffer);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
LONG
|
||||
QueryTimeZoneData(
|
||||
IN HKEY hZoneKey,
|
||||
OUT PULONG Index OPTIONAL,
|
||||
OUT PREG_TZI_FORMAT TimeZoneInfo,
|
||||
OUT PWCHAR Description OPTIONAL,
|
||||
IN OUT PULONG DescriptionSize OPTIONAL,
|
||||
OUT PWCHAR StandardName OPTIONAL,
|
||||
IN OUT PULONG StandardNameSize OPTIONAL,
|
||||
OUT PWCHAR DaylightName OPTIONAL,
|
||||
IN OUT PULONG DaylightNameSize OPTIONAL)
|
||||
{
|
||||
LONG lError;
|
||||
DWORD dwValueSize;
|
||||
|
||||
if (Description && DescriptionSize && *DescriptionSize > 0)
|
||||
{
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Display",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)Description,
|
||||
DescriptionSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
}
|
||||
|
||||
if (StandardName && StandardNameSize && *StandardNameSize > 0)
|
||||
{
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Std",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)StandardName,
|
||||
StandardNameSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
}
|
||||
|
||||
if (DaylightName && DaylightNameSize && *DaylightNameSize > 0)
|
||||
{
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Dlt",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)DaylightName,
|
||||
DaylightNameSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
}
|
||||
|
||||
if (Index)
|
||||
{
|
||||
dwValueSize = sizeof(*Index);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"Index",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)Index,
|
||||
&dwValueSize);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return lError;
|
||||
}
|
||||
|
||||
dwValueSize = sizeof(*TimeZoneInfo);
|
||||
lError = RegQueryValueExW(hZoneKey,
|
||||
L"TZI",
|
||||
NULL,
|
||||
NULL,
|
||||
(LPBYTE)TimeZoneInfo,
|
||||
&dwValueSize);
|
||||
return lError;
|
||||
}
|
||||
|
||||
//
|
||||
// NOTE: Very similar to the EnumDynamicTimeZoneInformation() function
|
||||
// introduced in Windows 8.
|
||||
//
|
||||
VOID
|
||||
EnumerateTimeZoneList(
|
||||
IN PENUM_TIMEZONE_CALLBACK Callback,
|
||||
IN PVOID Context OPTIONAL)
|
||||
{
|
||||
LONG lError;
|
||||
HKEY hZonesKey;
|
||||
HKEY hZoneKey;
|
||||
DWORD dwIndex;
|
||||
DWORD dwNameSize;
|
||||
WCHAR szKeyName[256];
|
||||
|
||||
/* Open the registry key containing the list of time zones */
|
||||
lError = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Time Zones",
|
||||
0,
|
||||
KEY_ENUMERATE_SUB_KEYS,
|
||||
&hZonesKey);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return;
|
||||
|
||||
/* Enumerate it */
|
||||
for (dwIndex = 0; ; dwIndex++)
|
||||
{
|
||||
dwNameSize = sizeof(szKeyName);
|
||||
lError = RegEnumKeyExW(hZonesKey,
|
||||
dwIndex,
|
||||
szKeyName,
|
||||
&dwNameSize,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL);
|
||||
// if (lError != ERROR_SUCCESS && lError != ERROR_MORE_DATA)
|
||||
if (lError == ERROR_NO_MORE_ITEMS)
|
||||
break;
|
||||
|
||||
/* Open the time zone sub-key */
|
||||
if (RegOpenKeyExW(hZonesKey,
|
||||
szKeyName,
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hZoneKey))
|
||||
{
|
||||
/* We failed, continue with another sub-key */
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Call the user-provided callback */
|
||||
lError = Callback(hZoneKey, Context);
|
||||
// lError = QueryTimeZoneData(hZoneKey, Context);
|
||||
|
||||
RegCloseKey(hZoneKey);
|
||||
}
|
||||
|
||||
RegCloseKey(hZonesKey);
|
||||
}
|
||||
|
||||
// Returns TRUE if AutoDaylight is ON.
|
||||
// Returns FALSE if AutoDaylight is OFF.
|
||||
BOOL
|
||||
GetAutoDaylight(VOID)
|
||||
{
|
||||
LONG lError;
|
||||
HKEY hKey;
|
||||
DWORD dwType;
|
||||
DWORD dwDisabled;
|
||||
DWORD dwValueSize;
|
||||
|
||||
lError = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\TimeZoneInformation",
|
||||
0,
|
||||
KEY_QUERY_VALUE,
|
||||
&hKey);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return FALSE;
|
||||
|
||||
// NOTE: On Vista+: REG_DWORD "DynamicDaylightTimeDisabled"
|
||||
dwValueSize = sizeof(dwDisabled);
|
||||
lError = RegQueryValueExW(hKey,
|
||||
L"DisableAutoDaylightTimeSet",
|
||||
NULL,
|
||||
&dwType,
|
||||
(LPBYTE)&dwDisabled,
|
||||
&dwValueSize);
|
||||
|
||||
RegCloseKey(hKey);
|
||||
|
||||
if ((lError != ERROR_SUCCESS) || (dwType != REG_DWORD) || (dwValueSize != sizeof(dwDisabled)))
|
||||
{
|
||||
/*
|
||||
* The call failed (non zero) because the registry value isn't available,
|
||||
* which means auto-daylight shouldn't be disabled.
|
||||
*/
|
||||
dwDisabled = FALSE;
|
||||
}
|
||||
|
||||
return !dwDisabled;
|
||||
}
|
||||
|
||||
VOID
|
||||
SetAutoDaylight(
|
||||
IN BOOL EnableAutoDaylightTime)
|
||||
{
|
||||
LONG lError;
|
||||
HKEY hKey;
|
||||
DWORD dwDisabled = TRUE;
|
||||
|
||||
lError = RegOpenKeyExW(HKEY_LOCAL_MACHINE,
|
||||
L"SYSTEM\\CurrentControlSet\\Control\\TimeZoneInformation",
|
||||
0,
|
||||
KEY_SET_VALUE,
|
||||
&hKey);
|
||||
if (lError != ERROR_SUCCESS)
|
||||
return;
|
||||
|
||||
if (!EnableAutoDaylightTime)
|
||||
{
|
||||
/* Auto-Daylight disabled: set the value to TRUE */
|
||||
// NOTE: On Vista+: REG_DWORD "DynamicDaylightTimeDisabled"
|
||||
RegSetValueExW(hKey,
|
||||
L"DisableAutoDaylightTimeSet",
|
||||
0,
|
||||
REG_DWORD,
|
||||
(LPBYTE)&dwDisabled,
|
||||
sizeof(dwDisabled));
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Auto-Daylight enabled: just delete the value */
|
||||
RegDeleteValueW(hKey, L"DisableAutoDaylightTimeSet");
|
||||
}
|
||||
|
||||
RegCloseKey(hKey);
|
||||
}
|
56
sdk/lib/tzlib/tzlib.h
Normal file
56
sdk/lib/tzlib/tzlib.h
Normal file
|
@ -0,0 +1,56 @@
|
|||
/*
|
||||
* PROJECT: ReactOS TimeZone Utilities Library
|
||||
* LICENSE: GPL-2.0 (https://spdx.org/licenses/GPL-2.0)
|
||||
* PURPOSE: Provides time-zone utility wrappers around Win32 functions,
|
||||
* that are used by different ReactOS modules such as
|
||||
* timedate.cpl, syssetup.dll.
|
||||
* COPYRIGHT: Copyright 2004-2005 Eric Kohl
|
||||
* Copyright 2016 Carlo Bramini
|
||||
* Copyright 2020 Hermes Belusca-Maito
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
typedef struct _REG_TZI_FORMAT
|
||||
{
|
||||
LONG Bias;
|
||||
LONG StandardBias;
|
||||
LONG DaylightBias;
|
||||
SYSTEMTIME StandardDate;
|
||||
SYSTEMTIME DaylightDate;
|
||||
} REG_TZI_FORMAT, *PREG_TZI_FORMAT;
|
||||
|
||||
typedef LONG
|
||||
(*PENUM_TIMEZONE_CALLBACK)(
|
||||
IN HKEY hZoneKey,
|
||||
IN PVOID Context OPTIONAL);
|
||||
|
||||
BOOL
|
||||
GetTimeZoneListIndex(
|
||||
IN OUT PULONG pIndex);
|
||||
|
||||
LONG
|
||||
QueryTimeZoneData(
|
||||
IN HKEY hZoneKey,
|
||||
OUT PULONG Index OPTIONAL,
|
||||
OUT PREG_TZI_FORMAT TimeZoneInfo,
|
||||
OUT PWCHAR Description OPTIONAL,
|
||||
IN OUT PULONG DescriptionSize OPTIONAL,
|
||||
OUT PWCHAR StandardName OPTIONAL,
|
||||
IN OUT PULONG StandardNameSize OPTIONAL,
|
||||
OUT PWCHAR DaylightName OPTIONAL,
|
||||
IN OUT PULONG DaylightNameSize OPTIONAL);
|
||||
|
||||
VOID
|
||||
EnumerateTimeZoneList(
|
||||
IN PENUM_TIMEZONE_CALLBACK Callback,
|
||||
IN PVOID Context OPTIONAL);
|
||||
|
||||
// Returns TRUE if AutoDaylight is ON.
|
||||
// Returns FALSE if AutoDaylight is OFF.
|
||||
BOOL
|
||||
GetAutoDaylight(VOID);
|
||||
|
||||
VOID
|
||||
SetAutoDaylight(
|
||||
IN BOOL EnableAutoDaylightTime);
|
Loading…
Reference in a new issue