[client,common] add option to set timezone

* /timezone now allows setting the timezone used from a windows timezone
  key name
* /list:timezones now lists all available windows timezone key names
This commit is contained in:
akallabeth 2024-04-23 15:40:04 +02:00
parent 9eb484b21b
commit 6c682c8418
No known key found for this signature in database
GPG Key ID: A49454A3FC909FD5
4 changed files with 81 additions and 8 deletions

View File

@ -30,6 +30,7 @@
#include <winpr/path.h>
#include <winpr/ncrypt.h>
#include <winpr/environment.h>
#include <winpr/timezone.h>
#include <freerdp/freerdp.h>
#include <freerdp/addin.h>
@ -1666,11 +1667,24 @@ static void freerdp_client_print_keyboard_list(void)
RDP_KEYBOARD_LAYOUT_TYPE_IME);
}
static void freerdp_client_print_timezone_list(void)
{
DWORD index = 0;
DYNAMIC_TIME_ZONE_INFORMATION info = { 0 };
while (EnumDynamicTimeZoneInformation(index++, &info) != ERROR_NO_MORE_ITEMS)
{
char TimeZoneKeyName[ARRAYSIZE(info.TimeZoneKeyName) + 1] = { 0 };
ConvertWCharNToUtf8(info.TimeZoneKeyName, ARRAYSIZE(info.TimeZoneKeyName), TimeZoneKeyName,
ARRAYSIZE(TimeZoneKeyName));
printf("%" PRIu32 ": '%s'\n", index, TimeZoneKeyName);
}
}
static void freerdp_client_print_tune_list(const rdpSettings* settings)
{
SSIZE_T type = 0;
printf("%s\t%50s\t%s\t%s", "<index>", "<key>", "<type>", "<default value>\n");
for (size_t x = 0; x < FreeRDP_Settings_StableAPI_MAX; x++)
{
const char* name = freerdp_settings_get_name_for_key(x);
@ -1755,7 +1769,9 @@ int freerdp_client_settings_command_line_status_print_ex(rdpSettings* settings,
if (arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT)
{
if (option_equals("tune", arg->Value))
if (option_equals("timezones", arg->Value))
freerdp_client_print_timezone_list();
else if (option_equals("tune", arg->Value))
freerdp_client_print_tune_list(settings);
else if (option_equals("kbd", arg->Value))
freerdp_client_print_keyboard_list();
@ -4718,6 +4734,43 @@ static int freerdp_client_settings_parse_command_line_arguments_int(
if (!freerdp_settings_set_uint32(settings, FreeRDP_TcpAckTimeout, (UINT32)val))
return fail_at(arg, COMMAND_LINE_ERROR_UNEXPECTED_VALUE);
}
CommandLineSwitchCase(arg, "timezone")
{
BOOL found = FALSE;
DWORD index = 0;
DYNAMIC_TIME_ZONE_INFORMATION info = { 0 };
char TimeZoneKeyName[ARRAYSIZE(info.TimeZoneKeyName) + 1] = { 0 };
while (EnumDynamicTimeZoneInformation(index++, &info) != ERROR_NO_MORE_ITEMS)
{
ConvertWCharNToUtf8(info.TimeZoneKeyName, ARRAYSIZE(info.TimeZoneKeyName),
TimeZoneKeyName, ARRAYSIZE(TimeZoneKeyName));
if (strncmp(TimeZoneKeyName, arg->Value, ARRAYSIZE(TimeZoneKeyName)) == 0)
{
found = TRUE;
break;
}
}
if (!found)
return fail_at(arg, COMMAND_LINE_ERROR_UNEXPECTED_VALUE);
if (!freerdp_settings_set_string(settings, FreeRDP_DynamicDSTTimeZoneKeyName,
TimeZoneKeyName))
return fail_at(arg, COMMAND_LINE_ERROR);
TIME_ZONE_INFORMATION* tz =
freerdp_settings_get_pointer_writable(settings, FreeRDP_ClientTimeZone);
if (!tz)
return fail_at(arg, COMMAND_LINE_ERROR_MEMORY);
tz->Bias = info.Bias;
tz->DaylightBias = info.DaylightBias;
tz->DaylightDate = info.DaylightDate;
memcpy(tz->DaylightName, info.DaylightName, sizeof(tz->DaylightName));
tz->StandardBias = info.StandardBias;
tz->StandardDate = info.StandardDate;
memcpy(tz->StandardName, info.StandardName, sizeof(tz->StandardName));
}
CommandLineSwitchCase(arg, "aero")
{
if (!freerdp_settings_set_bool(settings, FreeRDP_AllowDesktopComposition, enable))

View File

@ -297,7 +297,7 @@ static const COMMAND_LINE_ARGUMENT_A global_cmd_args[] = {
{ "list", COMMAND_LINE_VALUE_REQUIRED | COMMAND_LINE_PRINT,
"[kbd|kbd-scancode|kbd-lang[:<value>]|smartcard[:[pkinit-anchors:<path>][,pkcs11-module:<"
"name>]]|"
"monitor|tune]",
"monitor|tune|timezones]",
"List available options for subcommand", NULL, -1, NULL,
"List available options for subcommand" },
{ "log-filters", COMMAND_LINE_VALUE_REQUIRED, "<tag>:<level>[,<tag>:<level>[,...]]", NULL, NULL,
@ -453,6 +453,9 @@ static const COMMAND_LINE_ARGUMENT_A global_cmd_args[] = {
{ "timeout", COMMAND_LINE_VALUE_REQUIRED, "<time in ms>", "9000", NULL, -1, "timeout",
"Advanced setting for high latency links: Adjust connection timeout, use if you encounter "
"timeout failures with your connection" },
{ "timezone", COMMAND_LINE_VALUE_REQUIRED, "<windows timezone>", NULL, NULL, -1, NULL,
"Use supplied windows timezone for connection (requires server support), see /list:timezones "
"for allowed values" },
{ "tls", COMMAND_LINE_VALUE_REQUIRED, "[ciphers|seclevel|secrets-file|enforce]", NULL, NULL, -1,
NULL,
"TLS configuration options:"

View File

@ -110,6 +110,8 @@ extern "C"
const PDYNAMIC_TIME_ZONE_INFORMATION lpTimeZoneInformation, LPDWORD FirstYear,
LPDWORD LastYear);
#else
#pragma comment(lib, "advapi32")
#endif
#ifdef __cplusplus

View File

@ -38,9 +38,7 @@
#include "TimeZoneNameMap.h"
#include "TimeZoneIanaAbbrevMap.h"
#ifdef _WIN32
#pragma comment(lib, "advapi32")
#else
#ifndef _WIN32
#include <time.h>
#include <unistd.h>
@ -845,7 +843,7 @@ BOOL TzSpecificLocalTimeToSystemTimeEx(const DYNAMIC_TIME_ZONE_INFORMATION* lpTi
#endif
#if !defined(_WIN32) || (defined(_WIN32) && (_WIN32_WINNT < 0x0602)) /* Windows 8 */
#if !defined(_WIN32)
DWORD EnumDynamicTimeZoneInformation(const DWORD dwIndex,
PDYNAMIC_TIME_ZONE_INFORMATION lpTimeZoneInformation)
@ -909,7 +907,24 @@ DWORD GetDynamicTimeZoneInformationEffectiveYears(
WINPR_UNUSED(lpTimeZoneInformation);
WINPR_UNUSED(FirstYear);
WINPR_UNUSED(LastYear);
return 0;
return ERROR_FILE_NOT_FOUND;
}
#elif _WIN32_WINNT < 0x0602 /* Windows 8 */
DWORD EnumDynamicTimeZoneInformation(const DWORD dwIndex,
PDYNAMIC_TIME_ZONE_INFORMATION lpTimeZoneInformation)
{
WINPR_UNUSED(dwIndex);
WINPR_UNUSED(lpTimeZoneInformation);
return ERROR_NO_MORE_ITEMS;
}
DWORD GetDynamicTimeZoneInformationEffectiveYears(
const PDYNAMIC_TIME_ZONE_INFORMATION lpTimeZoneInformation, LPDWORD FirstYear, LPDWORD LastYear)
{
WINPR_UNUSED(lpTimeZoneInformation);
WINPR_UNUSED(FirstYear);
WINPR_UNUSED(LastYear);
return ERROR_FILE_NOT_FOUND;
}
#endif