1#include <freerdp/config.h>
3#include <freerdp/client.h>
4#include <freerdp/client/cmdline.h>
5#include <freerdp/settings.h>
6#include <winpr/cmdline.h>
8#include <winpr/strlst.h>
9#include <winpr/collections.h>
11typedef BOOL (*validate_settings_pr)(rdpSettings* settings);
12typedef void (*setup_settings_pr)(rdpSettings* settings);
14#define printref() printf("%s:%d: in function %-40s:", __FILE__, __LINE__, __func__)
16#define TEST_ERROR(format, ...) \
19 (void)fprintf(stderr, format, ##__VA_ARGS__); \
21 (void)printf(format, ##__VA_ARGS__); \
22 (void)fflush(stdout); \
25#define TEST_FAILURE(format, ...) \
29 (void)printf(" FAILURE "); \
30 (void)printf(format, ##__VA_ARGS__); \
31 (void)fflush(stdout); \
34static void print_test_title(
int argc,
char** argv)
36 printf(
"Running test:");
38 for (
int i = 0; i < argc; i++)
40 printf(
" %s", argv[i]);
46static inline BOOL testcase(
const char* name,
char** argv,
size_t argc,
int expected_return,
47 validate_settings_pr validate_settings,
48 setup_settings_pr setup_settings)
51 BOOL valid_settings = TRUE;
54 WINPR_ASSERT(argc <= INT_MAX);
56 print_test_title((
int)argc, argv);
60 TEST_ERROR(
"Test %s could not allocate settings!\n", name);
65 setup_settings(settings);
67 status = freerdp_client_settings_parse_command_line(settings, (
int)argc, argv, FALSE);
69 if (validate_settings)
71 valid_settings = validate_settings(settings);
76 if (status == expected_return)
85 TEST_FAILURE(
"Expected status %d, got status %d\n", expected_return, status);
93#define DRIVE_REDIRECT_PATH "c:\\Windows"
95#define DRIVE_REDIRECT_PATH "/tmp"
98static BOOL check_settings_gateway_response_timeout(rdpSettings* settings, UINT32 expected)
104 TEST_FAILURE(
"Expected GatewayResponseTimeout = %" PRIu32
", but got %" PRIu32
"!\n",
112static BOOL check_settings_gateway_response_timeout_default(rdpSettings* settings)
114 return check_settings_gateway_response_timeout(settings, 15000);
117static BOOL check_settings_gateway_response_timeout_custom(rdpSettings* settings)
119 return check_settings_gateway_response_timeout(settings, 120000);
122static const char test_aad_user_agent[] =
"TestAgent/1.0 (KHTML, like Gecko)";
124static BOOL check_settings_aad_user_agent(rdpSettings* settings)
127 if (!ua || (strcmp(ua, test_aad_user_agent) != 0))
129 TEST_FAILURE(
"Expected AadAuthUserAgent = \"%s\", but got %s!\n", test_aad_user_agent,
136static BOOL check_settings_smartcard_no_redirection(rdpSettings* settings)
142 TEST_FAILURE(
"Expected RedirectSmartCards = FALSE, but RedirectSmartCards = TRUE!\n");
146 if (freerdp_device_collection_find_type(settings, RDPDR_DTYP_SMARTCARD))
148 TEST_FAILURE(
"Expected no SMARTCARD device, but found at least one!\n");
155#ifndef TEST_SOURCE_DIR
156#error "TEST_SOURCE_DIR must be defined to the test source directory"
158#define DISABLED_DISPLAY_OPTIONS_RDP TEST_SOURCE_DIR "/rdp-cmdline/disabled-display-options.rdp"
160static BOOL check_settings_multimon_disabled(rdpSettings* settings)
166 TEST_FAILURE(
"Expected UseMultimon = FALSE, but UseMultimon = TRUE!\n");
172 TEST_FAILURE(
"Expected ForceMultimon = FALSE, but ForceMultimon = TRUE!\n");
178 TEST_FAILURE(
"Expected SmartSizing = TRUE, but SmartSizing = FALSE!\n");
185static BOOL check_settings_smart_sizing_disabled(rdpSettings* settings)
191 TEST_FAILURE(
"Expected SmartSizing = FALSE, but SmartSizing = TRUE!\n");
198 "Expected DynamicResolutionUpdate = TRUE, but DynamicResolutionUpdate = FALSE!\n");
204 TEST_FAILURE(
"Expected UseMultimon = TRUE, but UseMultimon = FALSE!\n");
211static BOOL check_settings_multimon_enabled(rdpSettings* settings)
217 TEST_FAILURE(
"Expected UseMultimon = TRUE, but UseMultimon = FALSE!\n");
224static void setup_settings_multimon_force(rdpSettings* settings)
229static BOOL check_settings_multimon_force(rdpSettings* settings)
235 TEST_FAILURE(
"Expected UseMultimon = TRUE, but UseMultimon = FALSE!\n");
241 TEST_FAILURE(
"Expected ForceMultimon = TRUE, but ForceMultimon = FALSE!\n");
248static BOOL check_settings_smart_sizing_size(rdpSettings* settings)
254 TEST_FAILURE(
"Expected SmartSizing = TRUE, but SmartSizing = FALSE!\n");
260 TEST_FAILURE(
"Expected SmartSizingWidth = 1024, but SmartSizingWidth = %u!\n",
267 TEST_FAILURE(
"Expected SmartSizingHeight = 768, but SmartSizingHeight = %u!\n",
275#if defined(WITH_GFX_AV1)
276static BOOL check_settings_gfx_av1(rdpSettings* settings)
282 TEST_FAILURE(
"Expected GfxCodecAV1 = TRUE, but GfxCodecAV1 = FALSE!\n");
290static BOOL check_settings_gfx_without_h264(rdpSettings* settings)
296 TEST_FAILURE(
"Expected ConnectionType = AUTODETECT, but ConnectionType = %u!\n",
306 "Expected the H.264 codecs off as /gfx asked, but /network:auto turned them on!\n");
312 TEST_FAILURE(
"Expected GfxProgressive = TRUE, but GfxProgressive = FALSE!\n");
319static BOOL check_settings_network_auto_h264(rdpSettings* settings)
326 TEST_FAILURE(
"Expected /network:auto alone to turn the H.264 codecs on!\n");
333static BOOL check_settings_modem_with_fonts(rdpSettings* settings)
339 TEST_FAILURE(
"Expected ConnectionType = MODEM, but ConnectionType = %u!\n",
346 TEST_FAILURE(
"Expected AllowFontSmoothing = TRUE as +fonts asked, but /network:modem "
353 TEST_FAILURE(
"Expected DisableWallpaper = TRUE, the default of /network:modem!\n");
361#define FLOATBAR_FLAG_POSITION_MASK 0xC0u
362#define FLOATBAR_FLAG_POSITION_LEFT 0x40u
363#define FLOATBAR_FLAG_POSITION_RIGHT 0x80u
366static BOOL check_floatbar_position(rdpSettings* settings, UINT32 expected_position_bits)
369 const UINT32 actual_position_bits = floatbar & FLOATBAR_FLAG_POSITION_MASK;
371 if (actual_position_bits != expected_position_bits)
373 TEST_FAILURE(
"Expected Floatbar position bits 0x%02" PRIx32
", got 0x%02" PRIx32
374 " (Floatbar=0x%08" PRIx32
")\n",
375 expected_position_bits, actual_position_bits, floatbar);
383static BOOL check_settings_floatbar_position_default(rdpSettings* settings)
385 return check_floatbar_position(settings, 0);
389static BOOL check_settings_floatbar_position_left(rdpSettings* settings)
391 return check_floatbar_position(settings, FLOATBAR_FLAG_POSITION_LEFT);
395static BOOL check_settings_floatbar_position_right(rdpSettings* settings)
397 return check_floatbar_position(settings, FLOATBAR_FLAG_POSITION_RIGHT);
403 validate_settings_pr validate_settings;
404 const char* command_line[128];
408 const char* expected_value;
409 } modified_arguments[8];
410 setup_settings_pr setup_settings;
414static const test tests[] = {
415 { COMMAND_LINE_STATUS_PRINT_HELP,
416 check_settings_smartcard_no_redirection,
417 {
"testfreerdp",
"--help",
nullptr },
418 { WINPR_C_ARRAY_INIT } },
419 { COMMAND_LINE_STATUS_PRINT_HELP,
420 check_settings_smartcard_no_redirection,
421 {
"testfreerdp",
"/help",
nullptr },
422 { WINPR_C_ARRAY_INIT } },
423 { COMMAND_LINE_STATUS_PRINT_HELP,
424 check_settings_smartcard_no_redirection,
425 {
"testfreerdp",
"-help",
nullptr },
426 { WINPR_C_ARRAY_INIT } },
427 { COMMAND_LINE_STATUS_PRINT_VERSION,
428 check_settings_smartcard_no_redirection,
429 {
"testfreerdp",
"--version",
nullptr },
430 { WINPR_C_ARRAY_INIT } },
431 { COMMAND_LINE_STATUS_PRINT_VERSION,
432 check_settings_smartcard_no_redirection,
433 {
"testfreerdp",
"/version",
nullptr },
434 { WINPR_C_ARRAY_INIT } },
435 { COMMAND_LINE_STATUS_PRINT_VERSION,
436 check_settings_smartcard_no_redirection,
437 {
"testfreerdp",
"-version",
nullptr },
438 { WINPR_C_ARRAY_INIT } },
440 check_settings_smartcard_no_redirection,
441 {
"testfreerdp",
"-v",
"test.freerdp.com",
nullptr },
442 { WINPR_C_ARRAY_INIT } },
444 check_settings_smartcard_no_redirection,
445 {
"testfreerdp",
"--v",
"test.freerdp.com",
nullptr },
446 { WINPR_C_ARRAY_INIT } },
448 check_settings_smartcard_no_redirection,
449 {
"testfreerdp",
"/v:test.freerdp.com",
nullptr },
450 { WINPR_C_ARRAY_INIT } },
452 check_settings_smartcard_no_redirection,
453 {
"testfreerdp",
"/sound",
"/drive:media," DRIVE_REDIRECT_PATH,
"/v:test.freerdp.com",
455 { WINPR_C_ARRAY_INIT } },
457 check_settings_smartcard_no_redirection,
458 {
"testfreerdp",
"-u",
"test",
"-p",
"test",
"-v",
"test.freerdp.com",
nullptr },
459 { { 4,
"****" }, WINPR_C_ARRAY_INIT } },
461 check_settings_smartcard_no_redirection,
462 {
"testfreerdp",
"/u:test",
"/p:test",
"/v:test.freerdp.com",
nullptr },
463 { { 2,
"/p:****" }, WINPR_C_ARRAY_INIT } },
464 { COMMAND_LINE_ERROR_NO_KEYWORD,
465 check_settings_smartcard_no_redirection,
466 {
"testfreerdp",
"-invalid",
nullptr },
467 { WINPR_C_ARRAY_INIT } },
468 { COMMAND_LINE_ERROR_NO_KEYWORD,
469 check_settings_smartcard_no_redirection,
470 {
"testfreerdp",
"--invalid",
nullptr },
471 { WINPR_C_ARRAY_INIT } },
472#if defined(WITH_FREERDP_DEPRECATED_CMDLINE)
473 { COMMAND_LINE_STATUS_PRINT,
474 check_settings_smartcard_no_redirection,
475 {
"testfreerdp",
"/kbd-list", 0 },
476 { WINPR_C_ARRAY_INIT } },
477 { COMMAND_LINE_STATUS_PRINT,
478 check_settings_smartcard_no_redirection,
479 {
"testfreerdp",
"/monitor-list", 0 },
480 { WINPR_C_ARRAY_INIT } },
482 { COMMAND_LINE_STATUS_PRINT,
483 check_settings_smartcard_no_redirection,
484 {
"testfreerdp",
"/list:kbd",
nullptr },
485 { WINPR_C_ARRAY_INIT } },
486 { COMMAND_LINE_STATUS_PRINT,
487 check_settings_smartcard_no_redirection,
488 {
"testfreerdp",
"/list:monitor",
nullptr },
489 { WINPR_C_ARRAY_INIT } },
491 check_settings_smartcard_no_redirection,
492 {
"testfreerdp",
"/sound",
"/drive:media:" DRIVE_REDIRECT_PATH,
"/v:test.freerdp.com",
494 { WINPR_C_ARRAY_INIT } },
496 check_settings_smartcard_no_redirection,
497 {
"testfreerdp",
"/sound",
"/drive:media,/foo/bar/blabla",
"/v:test.freerdp.com",
nullptr },
498 { WINPR_C_ARRAY_INIT } },
500 check_settings_gateway_response_timeout_default,
501 {
"testfreerdp",
"/gateway:type:arm,g:gw.contoso.com",
"/v:test.freerdp.com",
nullptr },
502 { WINPR_C_ARRAY_INIT } },
504 check_settings_gateway_response_timeout_custom,
505 {
"testfreerdp",
"/gateway:type:arm,g:gw.contoso.com,timeout:120000",
"/v:test.freerdp.com",
507 { WINPR_C_ARRAY_INIT } },
509 check_settings_gateway_response_timeout_custom,
510 {
"testfreerdp",
"/gateway:type:http,g:gw.contoso.com,timeout:120000",
"/v:test.freerdp.com",
512 { WINPR_C_ARRAY_INIT } },
513 { COMMAND_LINE_ERROR,
514 check_settings_gateway_response_timeout_default,
515 {
"testfreerdp",
"/gateway:type:arm,g:gw.contoso.com,timeout:0",
"/v:test.freerdp.com",
517 { WINPR_C_ARRAY_INIT } },
518 { COMMAND_LINE_ERROR,
519 check_settings_gateway_response_timeout_default,
520 {
"testfreerdp",
"/gateway:type:arm,g:gw.contoso.com,timeout:abc",
"/v:test.freerdp.com",
522 { WINPR_C_ARRAY_INIT } },
524 check_settings_aad_user_agent,
525 {
"testfreerdp",
"/azure:tenantid:common,\"user-agent:TestAgent/1.0 (KHTML, like Gecko)\"",
526 "/v:test.freerdp.com",
nullptr },
527 { WINPR_C_ARRAY_INIT } },
529 check_settings_multimon_disabled,
530 {
"testfreerdp", DISABLED_DISPLAY_OPTIONS_RDP,
"/multimon:off",
nullptr },
531 { WINPR_C_ARRAY_INIT },
532 setup_settings_multimon_force },
534 check_settings_multimon_disabled,
535 {
"testfreerdp", DISABLED_DISPLAY_OPTIONS_RDP,
"-multimon",
nullptr },
536 { WINPR_C_ARRAY_INIT },
537 setup_settings_multimon_force },
539 check_settings_smart_sizing_disabled,
540 {
"testfreerdp", DISABLED_DISPLAY_OPTIONS_RDP,
"-smart-sizing",
nullptr },
541 { WINPR_C_ARRAY_INIT } },
543 check_settings_smart_sizing_disabled,
544 {
"testfreerdp", DISABLED_DISPLAY_OPTIONS_RDP,
"/smart-sizing:off",
nullptr },
545 { WINPR_C_ARRAY_INIT } },
547 check_settings_multimon_force,
548 {
"testfreerdp",
"--multimon",
"force",
nullptr },
549 { WINPR_C_ARRAY_INIT } },
551 check_settings_smart_sizing_size,
552 {
"testfreerdp",
"--smart-sizing",
"1024x768",
nullptr },
553 { WINPR_C_ARRAY_INIT } },
554 { COMMAND_LINE_ERROR_UNEXPECTED_VALUE,
555 check_settings_smartcard_no_redirection,
556 {
"testfreerdp",
"/multimon:garbage",
nullptr },
557 { WINPR_C_ARRAY_INIT } },
558 { COMMAND_LINE_ERROR_UNEXPECTED_VALUE,
559 check_settings_smartcard_no_redirection,
560 {
"testfreerdp",
"/smart-sizing:garbage",
nullptr },
561 { WINPR_C_ARRAY_INIT } },
562 { COMMAND_LINE_ERROR_UNEXPECTED_VALUE,
563 check_settings_smartcard_no_redirection,
564 {
"testfreerdp",
"/multimon:",
nullptr },
565 { WINPR_C_ARRAY_INIT } },
566 { COMMAND_LINE_ERROR_UNEXPECTED_VALUE,
567 check_settings_smartcard_no_redirection,
568 {
"testfreerdp",
"/smart-sizing:",
nullptr },
569 { WINPR_C_ARRAY_INIT } },
571 check_settings_multimon_enabled,
572 {
"testfreerdp",
"+multimon",
nullptr },
573 { WINPR_C_ARRAY_INIT } },
574#if defined(WITH_GFX_H264)
576 check_settings_gfx_without_h264,
577 {
"testfreerdp",
"/gfx:progressive,AVC420:off,AVC444:off",
"/network:auto",
578 "/v:test.freerdp.com",
nullptr },
579 { WINPR_C_ARRAY_INIT } },
581 check_settings_gfx_without_h264,
582 {
"testfreerdp",
"/network:auto",
"/gfx:progressive,AVC420:off,AVC444:off",
583 "/v:test.freerdp.com",
nullptr },
584 { WINPR_C_ARRAY_INIT } },
586 check_settings_network_auto_h264,
587 {
"testfreerdp",
"/network:auto",
"/v:test.freerdp.com",
nullptr },
588 { WINPR_C_ARRAY_INIT } },
590#if defined(WITH_GFX_AV1)
592 check_settings_gfx_av1,
593 {
"testfreerdp",
"/gfx:AV1",
"/v:test.freerdp.com",
nullptr },
594 { WINPR_C_ARRAY_INIT } },
596 check_settings_gfx_av1,
597 {
"testfreerdp",
"/gfx:AV1:on",
"/v:test.freerdp.com",
nullptr },
598 { WINPR_C_ARRAY_INIT } },
601 check_settings_modem_with_fonts,
602 {
"testfreerdp",
"+fonts",
"/network:modem",
"/v:test.freerdp.com",
nullptr },
603 { WINPR_C_ARRAY_INIT } },
605 check_settings_floatbar_position_default,
606 {
"testfreerdp",
"/floatbar",
"/v:test.freerdp.com",
nullptr },
607 { WINPR_C_ARRAY_INIT } },
609 check_settings_floatbar_position_left,
610 {
"testfreerdp",
"/floatbar:position:left",
"/v:test.freerdp.com",
nullptr },
611 { WINPR_C_ARRAY_INIT } },
613 check_settings_floatbar_position_right,
614 {
"testfreerdp",
"/floatbar:position:right",
"/v:test.freerdp.com",
nullptr },
615 { WINPR_C_ARRAY_INIT } },
617 check_settings_floatbar_position_default,
618 {
"testfreerdp",
"/floatbar:position:center",
"/v:test.freerdp.com",
nullptr },
619 { WINPR_C_ARRAY_INIT } },
621 check_settings_floatbar_position_left,
622 {
"testfreerdp",
"/floatbar:sticky:on,default:visible,show:always,position:left",
623 "/v:test.freerdp.com",
nullptr },
624 { WINPR_C_ARRAY_INIT } },
625 { COMMAND_LINE_ERROR_UNEXPECTED_VALUE,
627 {
"testfreerdp",
"/floatbar:position:bogus",
"/v:test.freerdp.com",
nullptr },
628 { WINPR_C_ARRAY_INIT } },
632static void check_modified_arguments(
const test* test,
char** command_line,
int* rc)
634 const char* expected_argument =
nullptr;
636 for (
int k = 0; (expected_argument = test->modified_arguments[k].expected_value); k++)
638 int index = test->modified_arguments[k].index;
639 char* actual_argument = command_line[index];
641 if (0 != strcmp(actual_argument, expected_argument))
644 printf(
"Failure: overridden argument %d is %s but it should be %s\n", index,
645 actual_argument, expected_argument);
646 (void)fflush(stdout);
652int TestClientCmdLine(
int argc,
char* argv[])
658 for (
size_t i = 0; i < ARRAYSIZE(tests); i++)
660 const test* current = &tests[i];
662 char** command_line = string_list_copy(current->command_line);
664 const int len = string_list_length((
const char*
const*)command_line);
665 if (!testcase(__func__, command_line, WINPR_ASSERTING_INT_CAST(
size_t, len),
666 current->expected_status, current->validate_settings,
667 current->setup_settings))
669 TEST_FAILURE(
"parsing arguments.\n");
673 check_modified_arguments(current, command_line, &failure);
677 string_list_print(stdout, (
const char*
const*)command_line);
681 string_list_free(command_line);
FREERDP_API rdpSettings * freerdp_settings_new(DWORD flags)
creates a new setting struct
WINPR_ATTR_NODISCARD FREERDP_API const char * freerdp_settings_get_string(const rdpSettings *settings, FreeRDP_Settings_Keys_String id)
Returns a immutable string settings value.
WINPR_ATTR_NODISCARD FREERDP_API BOOL freerdp_settings_set_bool(rdpSettings *settings, FreeRDP_Settings_Keys_Bool id, BOOL val)
Sets a BOOL settings value.
FREERDP_API void freerdp_settings_free(rdpSettings *settings)
Free a settings struct with all data in it.
WINPR_ATTR_NODISCARD FREERDP_API UINT32 freerdp_settings_get_uint32(const rdpSettings *settings, FreeRDP_Settings_Keys_UInt32 id)
Returns a UINT32 settings value.
WINPR_ATTR_NODISCARD FREERDP_API BOOL freerdp_settings_get_bool(const rdpSettings *settings, FreeRDP_Settings_Keys_Bool id)
Returns a boolean settings value.