diff --git a/.travis.yml b/.travis.yml index 12a1427..71b755e 100644 --- a/.travis.yml +++ b/.travis.yml @@ -36,14 +36,15 @@ addons: - libudev-dev - autopoint - faketime + - libcmocka-dev homebrew: packages: - libusb - gettext -# Ensure that gettext is available on OSX +# Ensure that build dependencies are available on OSX before_script: - - if [ "$TRAVIS_OS_NAME" = osx ]; then brew install libusb gettext ; fi + - if [ "$TRAVIS_OS_NAME" = osx ]; then brew install libusb gettext cmocka ; fi # Enable parallel make env: diff --git a/configure.ac b/configure.ac index 6599a1e..7e1e294 100644 --- a/configure.ac +++ b/configure.ac @@ -17,6 +17,17 @@ LT_INIT PKG_PROG_PKG_CONFIG PKG_INSTALLDIR AX_COMPILER_FLAGS +AC_CANONICAL_HOST + +AC_MSG_NOTICE([Detected host OS is ${host_os}]) +build_linux=no +# Detect target system +case "${host_os}" in + linux*) + build_linux=yes + ;; +esac +AM_CONDITIONAL([LINUX], [test "x${build_linux}" = "xyes"]) # Internationalization AM_GNU_GETTEXT([external]) @@ -62,6 +73,12 @@ AM_COND_IF([HAVE_DOXYGEN], [AC_CONFIG_FILES([Doxyfile])], [AC_MSG_WARN(["Doxygen not found; continuing without doxygen support"])]) +# cmocka unit tests +AX_PKG_CHECK_MODULES([CMOCKA], [cmocka >= 1.1], [], [have_cmocka=yes], [have_cmocka=no]) +AM_CONDITIONAL([HAVE_CMOCKA], [test "x$have_cmocka" = xyes]) +AM_COND_IF([HAVE_CMOCKA], [], + [AC_MSG_WARN(["cmocka not found; disabling unit test build"])]) + # Check for the presence of tm_gmtoff in struct tm. If we have this, then we # can use it to determine the true GMT offset AC_CHECK_MEMBERS([struct tm.tm_gmtoff],, diff --git a/lib/libx52/Makefile.am b/lib/libx52/Makefile.am index 7c01736..43114ce 100644 --- a/lib/libx52/Makefile.am +++ b/lib/libx52/Makefile.am @@ -31,25 +31,28 @@ x52include_HEADERS = libx52.h # pkg-config files pkgconfig_DATA = libx52.pc -check_PROGRAMS = test_offset test_led test_blink_shift - -test_offset_SOURCES = test_offset.c test_common.c -test_offset_CFLAGS = @LIBUSB_CFLAGS@ -test_offset_LDADD = libx52.la - -test_led_SOURCES = test_led.c test_common.c -test_led_CFLAGS = @LIBUSB_CFLAGS@ -test_led_LDADD = libx52.la - -test_blink_shift_SOURCES = test_blink_shift.c test_common.c -test_blink_shift_CFLAGS = @LIBUSB_CFLAGS@ -test_blink_shift_LDADD = libx52.la - +if HAVE_CMOCKA LOG_DRIVER = env AM_TAP_AWK='$(AWK)' $(SHELL) $(top_srcdir)/tap-driver.sh -TESTS = test_offset test_led test_blink_shift +TESTS = libx52test +check_PROGRAMS = libx52test + +nodist_libx52test_SOURCES = test_libx52.c +libx52test_SOURCES = $(libx52_la_SOURCES) +libx52test_CFLAGS = @LIBUSB_CFLAGS@ -DLOCALEDIR='"$(localedir)"' -I $(top_srcdir) +libx52test_CFLAGS += -Dlibusb_control_transfer=__wrap_libusb_control_transfer +libx52test_LDFLAGS = @CMOCKA_LIBS@ @LIBUSB_LIBS@ +libx52test_LDADD = libx52.la + +CLEANFILES = test_libx52.c +test_libx52.c: $(srcdir)/x52_test_gen.py $(srcdir)/x52_tests.json + $(AM_V_GEN) $(PYTHON) $(srcdir)/x52_test_gen.py $(srcdir)/x52_tests.json > $@ +endif # Extra files that need to be in the distribution -EXTRA_DIST = libx52.h x52_commands.h x52_common.h test_common.h README.md +EXTRA_DIST = libx52.h x52_commands.h x52_common.h README.md + +# Add test files to the distribution +EXTRA_DIST += x52_test_gen.py x52_tests.json # Add documentation files to the distribution EXTRA_DIST += \ diff --git a/lib/libx52/test_blink_shift.c b/lib/libx52/test_blink_shift.c deleted file mode 100644 index df54d6b..0000000 --- a/lib/libx52/test_blink_shift.c +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Saitek X52 Pro MFD & LED driver - * Test program for validating blink and shift functionality - * - * Copyright (C) 2020 Nirenjan Krishnan (nirenjan@nirenjan.org) - * - * SPDX-License-Identifier: GPL-2.0-only WITH Classpath-exception-2.0 - */ - -#include -#include -#include -#include "x52_common.h" -#include "test_common.h" -#include "x52_commands.h" - -typedef int (*blink_shift_fn)(libx52_device *, uint8_t); - -TEST_STRUCT ( - blink_shift_fn func; - uint8_t state; - struct ivpair data[2]; -) - -#define on 1 -#define off 0 - -#define x52_shift_indicator 0xfd -#define x52_shift_on 0x51 -#define x52_shift_off 0x50 - -#define x52_blink_indicator 0xb4 -#define x52_blink_on 0x51 -#define x52_blink_off 0x50 - -#define TEST(func, state) { #func "/" #state, libx52_set_ ## func, state, {{ x52_ ## func ## _indicator, x52_ ## func ## _ ## state}, {0, 0}}} - -TEST_CASES = { - TEST(blink, on), - TEST(blink, off), - TEST(shift, on), - TEST(shift, off), -}; - -TEST_FUNC() -{ - TEST_INIT(); - int rc = (*test.func)(dev, test.state); - - if (rc != LIBX52_SUCCESS) { - PRINT_FAIL(); - printf("# Expected success, got %d\n", rc); - return; - } - - TEST_VERIFY(test.data); -} - -TEST_MAIN() diff --git a/lib/libx52/test_common.c b/lib/libx52/test_common.c deleted file mode 100644 index 25440e4..0000000 --- a/lib/libx52/test_common.c +++ /dev/null @@ -1,155 +0,0 @@ -/* - * Saitek X52 Pro MFD & LED driver - * Common functionality for test programs - * - * Copyright (C) 2020 Nirenjan Krishnan (nirenjan@nirenjan.org) - * - * SPDX-License-Identifier: GPL-2.0-only WITH Classpath-exception-2.0 - */ - -#define _GNU_SOURCE -#include -#include -#include -#include -#include -#include "x52_common.h" -#include "test_common.h" - -#define MAX_DIAGS 32 -#define MAX_DIAG_SZ 256 -static int diag_count; -static char diagnostic[MAX_DIAGS][MAX_DIAG_SZ]; - -#define ADD_DIAG(fmt_str, ...) do { \ - if (diag_count < MAX_DIAGS) { \ - snprintf(diagnostic[diag_count], MAX_DIAG_SZ, fmt_str, ##__VA_ARGS__); \ - diag_count++; \ - } \ -} while(0) - -/* Test vendor command function */ -int x52_test_vendor_command(libx52_device *dev, uint16_t index, uint16_t value) -{ - struct x52_vendor_data *vdata = (struct x52_vendor_data *)dev->hdl; - struct ivpair data = {index, value}; - - if (vdata->written < MAX_SZ) { - vdata->data[vdata->written] = data; - vdata->written++; - } - - return LIBX52_SUCCESS; -} - -/* Check expected data */ -bool x52_test_assert_expected(libx52_device *dev, struct ivpair *data) -{ - int written = 0; - struct x52_vendor_data *vdata = (struct x52_vendor_data *)dev->hdl; - - while((data[written].index != 0 || data[written].value != 0) && written < vdata->written) { - if ((data[written].index != vdata->data[written].index) || - (data[written].value != vdata->data[written].value)) { - ADD_DIAG("Mismatched data at position %d:", written); - ADD_DIAG("\tExpected: {%04x, %04x}", data[written].index, data[written].value); - ADD_DIAG("\tObserved: {%04x, %04x}", vdata->data[written].index, vdata->data[written].value); - return false; - } - - written++; - } - - if (data[written].index != 0 || data[written].value != 0) { - ADD_DIAG("data written %d", written); - ADD_DIAG("Insufficient data written, got only %d, additional expected:", written); - while (data[written].index != 0 && data[written].value != 0) { - ADD_DIAG("\t%04x %04x", data[written].index, data[written].value); - written++; - } - return false; - } - - if (vdata->written > written) { - ADD_DIAG("More data written, expected only %d, got %d", written, vdata->written); - return false; - } - - return true; -} - -void x52_test_print_diagnostics(void) -{ - int i; - for (i = 0; i < diag_count; i++) { - printf("# %s\n", diagnostic[i]); - } -} - -static void _x52_test_print_data(struct ivpair *data) -{ - while (data->index != 0 || data->value != 0) { - printf("%04x/%04x ", data->index, data->value); - data++; - } - puts(""); -} - -void x52_test_print_observed_data(libx52_device *dev) -{ - struct x52_vendor_data *vdata = (struct x52_vendor_data *)dev->hdl; - printf("Observed: "); - _x52_test_print_data(vdata->data); -} - -void x52_test_print_expected_data(struct ivpair *data) -{ - printf("Expected: "); - _x52_test_print_data(data); -} - -/* - * Initialize libx52, close any device handles, create a dummy handle - * and override the vendor command function. - */ -libx52_device *x52_test_init(void) -{ - libx52_device *dev; - struct x52_vendor_data *vdata; - int rc; - - rc = libx52_init(&dev); - if (rc != LIBX52_SUCCESS) { - fputs(libx52_strerror(rc), stderr); - exit(1); - } - - (void)libx52_disconnect(dev); - - /* Allocate memory for vendor data */ - vdata = calloc(1, sizeof(*vdata)); - if (vdata == NULL) { - perror("vendor data calloc"); - libx52_exit(dev); - return NULL; - } - - /* Reset the diagnostics buffers */ - memset(diagnostic, 0, sizeof(diagnostic)); - diag_count = 0; - - /* We don't need the device handle in test code, repurpose it */ - dev->hdl = (libusb_device_handle *)vdata; - - /* Setup vendor command function */ - dev->vendor_cmd_fn = x52_test_vendor_command; - - return dev; -} - -void x52_test_cleanup(libx52_device *dev) -{ - free(dev->hdl); - dev->hdl = NULL; - libx52_exit(dev); -} diff --git a/lib/libx52/test_common.h b/lib/libx52/test_common.h deleted file mode 100644 index 1aaa1a2..0000000 --- a/lib/libx52/test_common.h +++ /dev/null @@ -1,94 +0,0 @@ -/* - * Saitek X52 Pro MFD & LED driver - * Common functionality for test programs - * - * Copyright (C) 2020 Nirenjan Krishnan (nirenjan@nirenjan.org) - * - * SPDX-License-Identifier: GPL-2.0-only WITH Classpath-exception-2.0 - */ - -#ifndef _TEST_COMMON_H -#define _TEST_COMMON_H -#include -#include -#include "x52_common.h" - -/* ivpair is a pair of index and value fields that are passed to the - * test vendor command function. - */ -struct ivpair { - uint16_t index; - uint16_t value; -}; - -#define MAX_SZ 100 -struct x52_vendor_data { - int written; - struct ivpair data[MAX_SZ]; -}; - -/* - * Initialize libx52, close any device handles, create a dummy handle - * and override the vendor command function. - */ -libx52_device *x52_test_init(void); - -/* - * Check if expected data matches with written data. Terminate expected - * data with a pair of NULLs - */ -bool x52_test_assert_expected(libx52_device *dev, struct ivpair *data); - -/* Print diagnostics to screen */ -void x52_test_print_diagnostics(void); - -/* Cleanup test data */ -void x52_test_cleanup(libx52_device *dev); - -void x52_test_print_observed_data(libx52_device *dev); -void x52_test_print_expected_data(struct ivpair *data); - -#define PRINT_FAIL() printf("not ok %d %s\n", tc_id+1, test.test_case_id) -#define PRINT_PASS() printf("ok %d %s\n", tc_id+1, test.test_case_id) -#define TEST_STRUCT(...) struct test_case { \ - const char *test_case_id; \ - __VA_ARGS__ \ -}; - -#define TEST_CASES const struct test_case test_cases[] -#define TEST_FUNC() void run_test(int tc_id) -#define TEST_INIT() \ - struct libx52_device *dev = x52_test_init(); \ - struct test_case test = test_cases[tc_id]; - -#define TEST_VERIFY(data) do { \ - int test_rc; \ - test_rc = libx52_update(dev); \ - if (test_rc != LIBX52_SUCCESS) { \ - PRINT_FAIL(); \ - printf("# libx52_update failed, rc = %d\n", test_rc); \ - return; \ - } \ - \ - if (!x52_test_assert_expected(dev, data)) { \ - PRINT_FAIL(); \ - x52_test_print_diagnostics(); \ - x52_test_print_expected_data(data); \ - x52_test_print_observed_data(dev); \ - return; \ - } \ - \ - PRINT_PASS(); \ - x52_test_cleanup(dev); \ -} while(0) - -#define TEST_MAIN() int main() { \ - int i; \ - size_t tc_count = sizeof(test_cases) / sizeof(test_cases[0]); \ - printf("1..%lu\n", tc_count); \ - for (i = 0; i < tc_count; i++) { \ - run_test(i); \ - } \ -} - -#endif // !defined _TEST_COMMON_H diff --git a/lib/libx52/test_led.c b/lib/libx52/test_led.c deleted file mode 100644 index 16b9213..0000000 --- a/lib/libx52/test_led.c +++ /dev/null @@ -1,122 +0,0 @@ -/* - * Saitek X52 Pro MFD & LED driver - * Test program for validating LED sets - * - * Copyright (C) 2020 Nirenjan Krishnan (nirenjan@nirenjan.org) - * - * SPDX-License-Identifier: GPL-2.0-only WITH Classpath-exception-2.0 - */ - -#include -#include -#include -#include "x52_common.h" -#include "test_common.h" -#include "x52_commands.h" - -TEST_STRUCT ( - libx52_led_id led_id; - libx52_led_state state; - int retval; - struct ivpair data[3]; -) - -#define X52_LED_CMD 0xb8 -#define UNSUPPORTED(led, state) { #led "/" #state " unsupported", LIBX52_LED_ ## led, LIBX52_LED_STATE_ ## state, LIBX52_ERROR_NOT_SUPPORTED} -#define OFF_MONO(led) { #led "/Off", LIBX52_LED_## led, LIBX52_LED_STATE_OFF, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led) << 8)}, {0, 0}}} -#define ON(led) { #led "/On", LIBX52_LED_## led, LIBX52_LED_STATE_ON, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led) << 8) | 1}, {0, 0}}} -#define OFF_COLOR(led) { #led "/Off", LIBX52_LED_## led, LIBX52_LED_STATE_OFF, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led + 0) << 8)}, {X52_LED_CMD, ((LIBX52_LED_ ## led + 1) << 8)}, {0, 0}}} -#define RED(led) { #led "/Red", LIBX52_LED_## led, LIBX52_LED_STATE_RED, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led + 0) << 8) | 1}, {X52_LED_CMD, ((LIBX52_LED_ ## led + 1) << 8) | 0}, {0, 0}}} -#define AMBER(led) { #led "/Amber", LIBX52_LED_## led, LIBX52_LED_STATE_AMBER, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led + 0) << 8) | 1}, {X52_LED_CMD, ((LIBX52_LED_ ## led + 1) << 8) | 1}, {0, 0}}} -#define GREEN(led) { #led "/Green", LIBX52_LED_## led, LIBX52_LED_STATE_GREEN, LIBX52_SUCCESS, {{X52_LED_CMD, ((LIBX52_LED_ ## led + 0) << 8) | 0}, {X52_LED_CMD, ((LIBX52_LED_ ## led + 1) << 8) | 1}, {0, 0}}} - -TEST_CASES = { - OFF_MONO(FIRE), - ON(FIRE), - UNSUPPORTED(FIRE, RED), - UNSUPPORTED(FIRE, AMBER), - UNSUPPORTED(FIRE, GREEN), - - OFF_COLOR(A), - UNSUPPORTED(A, ON), - RED(A), - AMBER(A), - GREEN(A), - - OFF_COLOR(B), - UNSUPPORTED(B, ON), - RED(B), - AMBER(B), - GREEN(B), - - OFF_COLOR(D), - UNSUPPORTED(D, ON), - RED(D), - AMBER(D), - GREEN(D), - - OFF_COLOR(E), - UNSUPPORTED(E, ON), - RED(E), - AMBER(E), - GREEN(E), - - OFF_COLOR(T1), - UNSUPPORTED(T1, ON), - RED(T1), - AMBER(T1), - GREEN(T1), - - OFF_COLOR(T2), - UNSUPPORTED(T2, ON), - RED(T2), - AMBER(T2), - GREEN(T2), - - OFF_COLOR(T3), - UNSUPPORTED(T3, ON), - RED(T3), - AMBER(T3), - GREEN(T3), - - OFF_COLOR(POV), - UNSUPPORTED(POV, ON), - RED(POV), - AMBER(POV), - GREEN(POV), - - OFF_COLOR(CLUTCH), - UNSUPPORTED(CLUTCH, ON), - RED(CLUTCH), - AMBER(CLUTCH), - GREEN(CLUTCH), - - OFF_MONO(THROTTLE), - ON(THROTTLE), - UNSUPPORTED(THROTTLE, RED), - UNSUPPORTED(THROTTLE, AMBER), - UNSUPPORTED(THROTTLE, GREEN), -}; - - -TEST_FUNC() -{ - TEST_INIT(); - - /* Set the X52Pro flag in dev->flags, otherwise libx52_set_led_state will - * always return not supported - */ - dev->flags = 1; - - int rc = libx52_set_led_state(dev, test.led_id, test.state); - - if (rc != test.retval) { - PRINT_FAIL(); - printf("# Expected retval %d, got %d\n", test.retval, rc); - return; - } - - TEST_VERIFY(test.data); -} - -TEST_MAIN() diff --git a/lib/libx52/test_offset.c b/lib/libx52/test_offset.c deleted file mode 100644 index 6d48193..0000000 --- a/lib/libx52/test_offset.c +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Saitek X52 Pro MFD & LED driver - * Test program for validating offset calculation - * - * Copyright (C) 2020 Nirenjan Krishnan (nirenjan@nirenjan.org) - * - * SPDX-License-Identifier: GPL-2.0-only WITH Classpath-exception-2.0 - */ - -#include -#include -#include -#include "x52_common.h" -#include "test_common.h" - -TEST_STRUCT ( - int offset_primary; - int offset_secondary; - libx52_clock_id clock_id; - uint16_t x52_clock; - uint16_t x52_offset; -) - -#define TEST(id, o1, o23, offs) {id, o1, o23, LIBX52_CLOCK_2, 0xc1, offs}, {id, o1, o23, LIBX52_CLOCK_3, 0xc2, offs} - -TEST_CASES = { - TEST("Etc/UTC+24|Etc/UTC-24", -1440, +1440, 0), - TEST("Etc/UTC-24|Etc/UTC+24", +1440, -1440, 0x0400), // Negative 0 - TEST("Honolulu|Auckland", -600, +720, 0x0478), // -2 hours - TEST("Auckland|Honolulu", +720, -600, 0x0078), // +2 hours - TEST("Etc/UTC+12|Etc/UTC-14", -720, +840, 0x078), // +2 hours - TEST("Etc/UTC-14|Etc/UTC+12", +840, -720, 0x478), // -2 hours - TEST("PDT|UTC", -420, 0, 0x1a4), // +7 hours - TEST("UTC|PDT", 0, -420, 0x5a4), // -7 hours - TEST("PST|UTC", -480, 0, 0x1e0), // +8 hours - TEST("UTC|PST", 0, -480, 0x5e0), // -8 hours - TEST("Etc/UTC+12|Etc/UTC-12", -720, +720, 0), - TEST("Etc/UTC-12|Etc/UTC+12", +720, -720, 0x0400), -}; - -TEST_FUNC() -{ - TEST_INIT(); - int rc; - struct ivpair data[2] = { 0 }; - - dev->timezone[LIBX52_CLOCK_1] = test.offset_primary; - rc = libx52_set_clock_timezone(dev, test.clock_id, test.offset_secondary); - if (rc != LIBX52_SUCCESS) { - PRINT_FAIL(); - printf("# set_clock_timezone failed, rc = %d\n", rc); - return; - } - - data[0].index = test.x52_clock; - data[0].value = test.x52_offset; - TEST_VERIFY(data); -} - -TEST_MAIN(); diff --git a/lib/libx52/x52_common.h b/lib/libx52/x52_common.h index 8916e4a..c3e8533 100644 --- a/lib/libx52/x52_common.h +++ b/lib/libx52/x52_common.h @@ -25,8 +25,6 @@ #define X52_MFD_LINES 3 #define X52_MFD_CLOCKS 3 -typedef int (*x52_vendor_command)(libx52_device *x52, uint16_t index, uint16_t value); - struct x52_mfd_line { uint8_t text[X52_MFD_LINE_SIZE]; uint8_t length; @@ -53,7 +51,6 @@ struct libx52_device { int timezone[X52_MFD_CLOCKS]; libx52_clock_format time_format[X52_MFD_CLOCKS]; - x52_vendor_command vendor_cmd_fn; }; /** Flag bits */ @@ -108,6 +105,5 @@ static inline uint32_t tst_bit(uint32_t *value, uint32_t bit) } int _x52_translate_libusb_error(enum libusb_error errcode); -int _x52_vendor_command(libx52_device *x52, uint16_t index, uint16_t value); #endif /* !defined X52JOY_COMMON_H */ diff --git a/lib/libx52/x52_control.c b/lib/libx52/x52_control.c index dc3f0ed..420cfc3 100644 --- a/lib/libx52/x52_control.c +++ b/lib/libx52/x52_control.c @@ -66,11 +66,18 @@ int _x52_translate_libusb_error(enum libusb_error errcode) }; } -int _x52_vendor_command(libx52_device *x52, uint16_t index, uint16_t value) +int libx52_vendor_command(libx52_device *x52, uint16_t index, uint16_t value) { int j; int rc = 0; + /* It is possible for the vendor command to be called when the joystick + * is not connected. Check for this and return an appropriate error. + */ + if (!x52->hdl) { + return LIBX52_ERROR_NO_DEVICE; + } + /* Allow retry in case of failure */ for (j = 0; j < 3; j++) { rc = libusb_control_transfer(x52->hdl, @@ -82,22 +89,6 @@ int _x52_vendor_command(libx52_device *x52, uint16_t index, uint16_t value) } } - return rc; -} - -int libx52_vendor_command(libx52_device *x52, uint16_t index, uint16_t value) -{ - int rc = 0; - - /* It is possible for the vendor command to be called when the joystick - * is not connected. Check for this and return an appropriate error. - */ - if (!x52->hdl || !x52->vendor_cmd_fn) { - return LIBX52_ERROR_NO_DEVICE; - } - - rc = (*(x52->vendor_cmd_fn))(x52, index, value); - /* Handle device removal */ if (rc == LIBUSB_ERROR_NO_DEVICE) { /* Physical device has likely been disconnected, disconnect the virtual diff --git a/lib/libx52/x52_core.c b/lib/libx52/x52_core.c index fe42c58..8a0470d 100644 --- a/lib/libx52/x52_core.c +++ b/lib/libx52/x52_core.c @@ -61,7 +61,6 @@ int libx52_disconnect(libx52_device *dev) libusb_close(dev->hdl); dev->hdl = NULL; dev->flags = 0; - dev->vendor_cmd_fn = NULL; } return LIBX52_SUCCESS; @@ -103,9 +102,6 @@ int libx52_connect(libx52_device *dev) dev->hdl = hdl; - /* Use default vendor command function */ - dev->vendor_cmd_fn = _x52_vendor_command; - if (libx52_device_is_x52pro(desc.idProduct)) { set_bit(&(dev->flags), X52_FLAG_IS_PRO); } diff --git a/lib/libx52/x52_mfd_led.c b/lib/libx52/x52_mfd_led.c index a7f8074..80d5cbd 100644 --- a/lib/libx52/x52_mfd_led.c +++ b/lib/libx52/x52_mfd_led.c @@ -116,19 +116,21 @@ static int x52pro_set_led_state(libx52_device *x52, libx52_led_id led, libx52_le int libx52_set_led_state(libx52_device *x52, libx52_led_id led, libx52_led_state state) { + int rc; if (!x52) { return LIBX52_ERROR_INVALID_PARAM; } - if (tst_bit(&x52->flags, X52_FLAG_IS_PRO)) { + rc = libx52_check_feature(x52, LIBX52_FEATURE_LED); + if (rc == LIBX52_SUCCESS) { return x52pro_set_led_state(x52, led, state); } /* - * For now, we only support setting the LEDs on the X52 Pro model. + * The non-Pro X52 does not support setting individual LED states. * Calling this API on a non-Pro model will return a not supported error. */ - return LIBX52_ERROR_NOT_SUPPORTED; + return rc; } int libx52_set_brightness(libx52_device *x52, uint8_t mfd, uint16_t brightness) diff --git a/lib/libx52/x52_test_gen.py b/lib/libx52/x52_test_gen.py new file mode 100755 index 0000000..08c9539 --- /dev/null +++ b/lib/libx52/x52_test_gen.py @@ -0,0 +1,231 @@ +#!/usr/bin/env python3 +"""libx52 test generator program, writes test program to stdout""" + +import sys +import json + +_TEST_FILE_HEADER = """/* + * libx52 test program + * + * This file is automatically generated. DO NOT EDIT! + */ + +#include +#include +#include +#include +#include +#include +#include + +#include "x52_common.h" + +static int group_setup(void **state) +{ + libx52_device *dev; + int rc; + + rc = libx52_init(&dev); + if (rc != LIBX52_SUCCESS) { + return rc; + } + + /* Disconnect any potentially connected joysticks */ + (void)libx52_disconnect(dev); + + /* Create a dummy handle so that libx52_update doesn't abort early */ + dev->hdl = (void *)(uintptr_t)(-1); + + *state = dev; + + return 0; +} + +static int group_teardown(void **state) +{ + libx52_device *dev = *state; + + dev->hdl = NULL; + libx52_exit(dev); + return 0; +} + +static int test_setup(void **state) +{ + libx52_device *dev = *state; + void *context = dev->ctx; + void *handle = dev->hdl; + memset(dev, 0, sizeof(*dev)); + dev->ctx = context; + dev->hdl = handle; + /* Set flags to 1 to indicate that we are testing X52 Pro */ + dev->flags = 1; + + return 0; +} + +int __wrap_libusb_control_transfer(libusb_device_handle *dev_handle, + uint8_t request_type, + uint8_t bRequest, + uint16_t wValue, + uint16_t wIndex, + unsigned char *data, + uint16_t wLength, + unsigned int timeout) +{ + function_called(); + check_expected(wIndex); + check_expected(wValue); + assert_int_equal(request_type, + LIBUSB_REQUEST_TYPE_VENDOR | LIBUSB_RECIPIENT_DEVICE | LIBUSB_ENDPOINT_OUT); + assert_int_equal(bRequest, 0x91); + assert_null(data); + assert_int_equal(wLength, 0); + assert_int_equal(timeout, 5000); + + return mock(); +} + +""" + +_TEST_FUNCTION_HEADER = """ +static void {}(void **state) +{{ + libx52_device *dev = *state; + int rc; +""" + +_TEST_FUNCTION_FOOTER_NORMAL = """ + assert_int_equal(rc, LIBX52_SUCCESS); + + rc = libx52_update(dev); + assert_int_equal(rc, LIBX52_SUCCESS); +} +""" + +_TEST_FUNCTION_FOOTER_ERROR = """ + assert_int_equal(rc, LIBX52_ERROR_{}); +}} +""" + +class Test(): + """Test case class, single test""" + + def __init__(self, group, obj): + """Load test case from an object""" + self.function = group.function + self.name = group.name + self.params_prefix = group.params_prefix + self.params = obj["params"] + self.setup_hook = group.setup_hook + obj.get("setup_hook", []) + self.fields = group.fields.copy() + self.fields.update(obj.get("fields", {})) + + if len(self.params_prefix) < len(self.params): + self.params_prefix.extend([''] * (len(self.params) - len(self.params_prefix))) + + self.output = obj.get("output", []) + self.retval = obj.get("retval", "") + + def definition(self): + test_name = self.name + '_' + '_'.join(p.strip('"').replace('-','_') for p in self.params) + return test_name.lower() + + def print(self): + print(_TEST_FUNCTION_HEADER.format(self.definition())) + + if self.fields: + for arg, val in self.fields.items(): + print(" dev->{} = {};".format(arg, val)) + + if self.setup_hook: + # Setup hook is an array of C commands that need to be executed + # prior to setting up the wrapper and running the tests + for hook in self.setup_hook: + print(" {}".format(hook)) + + if self.output: + print(" expect_function_calls(__wrap_libusb_control_transfer, {});".format(len(self.output))) + print(" will_return_count(__wrap_libusb_control_transfer, LIBUSB_SUCCESS, {});".format(len(self.output))) + + for idx, val in self.output: + print(" expect_value(__wrap_libusb_control_transfer, wIndex, 0x{});".format(idx)) + print(" expect_value(__wrap_libusb_control_transfer, wValue, 0x{});".format(val)) + + params = ', '.join(''.join(p) for p in zip(self.params_prefix, self.params)) + print(" rc = {}(dev, {});".format(self.function, params)) + + if self.retval: + print(_TEST_FUNCTION_FOOTER_ERROR.format(self.retval)) + else: + print(_TEST_FUNCTION_FOOTER_NORMAL); + +_TEST_GROUP_HEADER = "const struct CMUnitTest tests[] = {" +_TEST_GROUP_FOOTER = "};" + +class TestGroup(): + """Test group class, contains multiple tests""" + + def __init__(self, name, obj): + """Load test cases from an object""" + self.name = name + self.function = obj["function"] + self.fields = obj.get("fields", {}) + self.setup_hook = obj.get("setup_hook", []) + self.params_prefix = obj.get("params_prefix", []) + self.tests = [] + for test in obj["tests"]: + self.tests.append(Test(self, test)) + + def definition(self): + return self.name.lower() + "_tests" + + def print(self): + """Print the test group""" + for test in self.tests: + test.print() + +_MAIN = """ +int main(void) +{ + cmocka_set_message_output(CM_OUTPUT_TAP); + cmocka_run_group_tests(tests, group_setup, group_teardown); + return 0; +} +""" + +class TestSuite(): + """Test suite class, contains multiple test cases""" + + def __init__(self, file): + """Load test suite""" + with open(file, 'r') as infile: + self.data = json.load(infile) + self.groups = [] + for group, obj in self.data.items(): + self.groups.append(TestGroup(group, obj)) + + def print(self): + print(_TEST_FILE_HEADER) + + for group in self.groups: + group.print() + + print(_TEST_GROUP_HEADER) + for group in self.groups: + for test in group.tests: + print(" cmocka_unit_test_setup({}, test_setup),".format(test.definition())) + print(_TEST_GROUP_FOOTER) + print(_MAIN) + + +def main(): + if len(sys.argv) != 2: + sys.stderr.write('Usage: %s \n' % + sys.argv[0]) + sys.exit(1) + + TestSuite(sys.argv[1]).print() + +if __name__ == "__main__": + main() diff --git a/lib/libx52/x52_tests.json b/lib/libx52/x52_tests.json new file mode 100644 index 0000000..f7a576d --- /dev/null +++ b/lib/libx52/x52_tests.json @@ -0,0 +1,2028 @@ +{ + "LED": { + "function": "libx52_set_led_state", + "params_prefix": ["LIBX52_LED_", "LIBX52_LED_STATE_"], + "tests": [ + { + "params": ["FIRE", "OFF"], + "output": [["00b8", "0100"]] + }, + { + "params": ["FIRE", "ON"], + "output": [["00b8", "0101"]] + }, + { + "params": ["FIRE", "RED"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["FIRE", "AMBER"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["FIRE", "GREEN"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["A", "OFF"], + "output": [["00b8", "0200"], ["00b8", "0300"]] + }, + { + "params": ["A", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["A", "RED"], + "output": [["00b8", "0201"], ["00b8", "0300"]] + }, + { + "params": ["A", "AMBER"], + "output": [["00b8", "0201"], ["00b8", "0301"]] + }, + { + "params": ["A", "GREEN"], + "output": [["00b8", "0200"], ["00b8", "0301"]] + }, + { + "params": ["B", "OFF"], + "output": [["00b8", "0400"], ["00b8", "0500"]] + }, + { + "params": ["B", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["B", "RED"], + "output": [["00b8", "0401"], ["00b8", "0500"]] + }, + { + "params": ["B", "AMBER"], + "output": [["00b8", "0401"], ["00b8", "0501"]] + }, + { + "params": ["B", "GREEN"], + "output": [["00b8", "0400"], ["00b8", "0501"]] + }, + { + "params": ["D", "OFF"], + "output": [["00b8", "0600"], ["00b8", "0700"]] + }, + { + "params": ["D", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["D", "RED"], + "output": [["00b8", "0601"], ["00b8", "0700"]] + }, + { + "params": ["D", "AMBER"], + "output": [["00b8", "0601"], ["00b8", "0701"]] + }, + { + "params": ["D", "GREEN"], + "output": [["00b8", "0600"], ["00b8", "0701"]] + }, + { + "params": ["E", "OFF"], + "output": [["00b8", "0800"], ["00b8", "0900"]] + }, + { + "params": ["E", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["E", "RED"], + "output": [["00b8", "0801"], ["00b8", "0900"]] + }, + { + "params": ["E", "AMBER"], + "output": [["00b8", "0801"], ["00b8", "0901"]] + }, + { + "params": ["E", "GREEN"], + "output": [["00b8", "0800"], ["00b8", "0901"]] + }, + { + "params": ["T1", "OFF"], + "output": [["00b8", "0a00"], ["00b8", "0b00"]] + }, + { + "params": ["T1", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["T1", "RED"], + "output": [["00b8", "0a01"], ["00b8", "0b00"]] + }, + { + "params": ["T1", "AMBER"], + "output": [["00b8", "0a01"], ["00b8", "0b01"]] + }, + { + "params": ["T1", "GREEN"], + "output": [["00b8", "0a00"], ["00b8", "0b01"]] + }, + { + "params": ["T2", "OFF"], + "output": [["00b8", "0c00"], ["00b8", "0d00"]] + }, + { + "params": ["T2", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["T2", "RED"], + "output": [["00b8", "0c01"], ["00b8", "0d00"]] + }, + { + "params": ["T2", "AMBER"], + "output": [["00b8", "0c01"], ["00b8", "0d01"]] + }, + { + "params": ["T2", "GREEN"], + "output": [["00b8", "0c00"], ["00b8", "0d01"]] + }, + { + "params": ["T3", "OFF"], + "output": [["00b8", "0e00"], ["00b8", "0f00"]] + }, + { + "params": ["T3", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["T3", "RED"], + "output": [["00b8", "0e01"], ["00b8", "0f00"]] + }, + { + "params": ["T3", "AMBER"], + "output": [["00b8", "0e01"], ["00b8", "0f01"]] + }, + { + "params": ["T3", "GREEN"], + "output": [["00b8", "0e00"], ["00b8", "0f01"]] + }, + { + "params": ["POV", "OFF"], + "output": [["00b8", "1000"], ["00b8", "1100"]] + }, + { + "params": ["POV", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["POV", "RED"], + "output": [["00b8", "1001"], ["00b8", "1100"]] + }, + { + "params": ["POV", "AMBER"], + "output": [["00b8", "1001"], ["00b8", "1101"]] + }, + { + "params": ["POV", "GREEN"], + "output": [["00b8", "1000"], ["00b8", "1101"]] + }, + { + "params": ["CLUTCH", "OFF"], + "output": [["00b8", "1200"], ["00b8", "1300"]] + }, + { + "params": ["CLUTCH", "ON"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["CLUTCH", "RED"], + "output": [["00b8", "1201"], ["00b8", "1300"]] + }, + { + "params": ["CLUTCH", "AMBER"], + "output": [["00b8", "1201"], ["00b8", "1301"]] + }, + { + "params": ["CLUTCH", "GREEN"], + "output": [["00b8", "1200"], ["00b8", "1301"]] + }, + { + "params": ["THROTTLE", "OFF"], + "output": [["00b8", "1400"]] + }, + { + "params": ["THROTTLE", "ON"], + "output": [["00b8", "1401"]] + }, + { + "params": ["THROTTLE", "RED"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["THROTTLE", "AMBER"], + "retval": "NOT_SUPPORTED" + }, + { + "params": ["THROTTLE", "GREEN"], + "retval": "NOT_SUPPORTED" + } + ] + }, + "LED_nonPro": { + "_comment": [ + "This suite checks if the LED state function returns not supported", + "when the device is an X52 (non-Pro) model" + ], + "function": "libx52_set_led_state", + "fields": { + "flags": "0" + }, + "params_prefix": ["LIBX52_LED_", "LIBX52_LED_STATE_"], + "tests": [ + { + "params": ["FIRE", "OFF"], + "retval": "NOT_SUPPORTED" + } + ] + }, + "MFD": { + "function": "libx52_set_text", + "tests": [ + { + "params": ["0", "\"\"", "0"], + "output": [ + ["00d9", "0000"] + ] + }, + { + "params": ["0", "\"a\"", "1"], + "output": [ + ["00d9", "0000"], + ["00d1", "2061"] + ] + }, + { + "params": ["0", "\"ab\"", "2"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"] + ] + }, + { + "params": ["0", "\"abc\"", "3"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "2063"] + ] + }, + { + "params": ["0", "\"abcd\"", "4"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"] + ] + }, + { + "params": ["0", "\"abcde\"", "5"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "2065"] + ] + }, + { + "params": ["0", "\"abcdef\"", "6"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"] + ] + }, + { + "params": ["0", "\"abcdefg\"", "7"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "2067"] + ] + }, + { + "params": ["0", "\"abcdefgh\"", "8"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"] + ] + }, + { + "params": ["0", "\"abcdefghi\"", "9"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "2069"] + ] + }, + { + "params": ["0", "\"abcdefghij\"", "10"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"] + ] + }, + { + "params": ["0", "\"abcdefghijk\"", "11"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "206b"] + ] + }, + { + "params": ["0", "\"abcdefghijkl\"", "12"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"] + ] + }, + { + "params": ["0", "\"abcdefghijklm\"", "13"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "206d"] + ] + }, + { + "params": ["0", "\"abcdefghijklmn\"", "14"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "6e6d"] + ] + }, + { + "params": ["0", "\"abcdefghijklmno\"", "15"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "6e6d"], + ["00d1", "206f"] + ] + }, + { + "params": ["0", "\"abcdefghijklmnop\"", "16"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "6e6d"], + ["00d1", "706f"] + ] + }, + { + "params": ["0", "\"abcdefghijklmnopq\"", "17"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "6e6d"], + ["00d1", "706f"] + ] + }, + { + "params": ["0", "\"abcdefghijklmnopqr\"", "18"], + "output": [ + ["00d9", "0000"], + ["00d1", "6261"], + ["00d1", "6463"], + ["00d1", "6665"], + ["00d1", "6867"], + ["00d1", "6a69"], + ["00d1", "6c6b"], + ["00d1", "6e6d"], + ["00d1", "706f"] + ] + }, + { + "params": ["1", "\"\"", "0"], + "output": [ + ["00da", "0000"] + ] + }, + { + "params": ["1", "\"a\"", "1"], + "output": [ + ["00da", "0000"], + ["00d2", "2061"] + ] + }, + { + "params": ["1", "\"ab\"", "2"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"] + ] + }, + { + "params": ["1", "\"abc\"", "3"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "2063"] + ] + }, + { + "params": ["1", "\"abcd\"", "4"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"] + ] + }, + { + "params": ["1", "\"abcde\"", "5"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "2065"] + ] + }, + { + "params": ["1", "\"abcdef\"", "6"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"] + ] + }, + { + "params": ["1", "\"abcdefg\"", "7"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "2067"] + ] + }, + { + "params": ["1", "\"abcdefgh\"", "8"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"] + ] + }, + { + "params": ["1", "\"abcdefghi\"", "9"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "2069"] + ] + }, + { + "params": ["1", "\"abcdefghij\"", "10"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"] + ] + }, + { + "params": ["1", "\"abcdefghijk\"", "11"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "206b"] + ] + }, + { + "params": ["1", "\"abcdefghijkl\"", "12"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"] + ] + }, + { + "params": ["1", "\"abcdefghijklm\"", "13"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "206d"] + ] + }, + { + "params": ["1", "\"abcdefghijklmn\"", "14"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "6e6d"] + ] + }, + { + "params": ["1", "\"abcdefghijklmno\"", "15"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "6e6d"], + ["00d2", "206f"] + ] + }, + { + "params": ["1", "\"abcdefghijklmnop\"", "16"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "6e6d"], + ["00d2", "706f"] + ] + }, + { + "params": ["1", "\"abcdefghijklmnopq\"", "17"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "6e6d"], + ["00d2", "706f"] + ] + }, + { + "params": ["1", "\"abcdefghijklmnopqr\"", "18"], + "output": [ + ["00da", "0000"], + ["00d2", "6261"], + ["00d2", "6463"], + ["00d2", "6665"], + ["00d2", "6867"], + ["00d2", "6a69"], + ["00d2", "6c6b"], + ["00d2", "6e6d"], + ["00d2", "706f"] + ] + }, + { + "params": ["2", "\"\"", "0"], + "output": [ + ["00dc", "0000"] + ] + }, + { + "params": ["2", "\"a\"", "1"], + "output": [ + ["00dc", "0000"], + ["00d4", "2061"] + ] + }, + { + "params": ["2", "\"ab\"", "2"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"] + ] + }, + { + "params": ["2", "\"abc\"", "3"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "2063"] + ] + }, + { + "params": ["2", "\"abcd\"", "4"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"] + ] + }, + { + "params": ["2", "\"abcde\"", "5"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "2065"] + ] + }, + { + "params": ["2", "\"abcdef\"", "6"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"] + ] + }, + { + "params": ["2", "\"abcdefg\"", "7"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "2067"] + ] + }, + { + "params": ["2", "\"abcdefgh\"", "8"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"] + ] + }, + { + "params": ["2", "\"abcdefghi\"", "9"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "2069"] + ] + }, + { + "params": ["2", "\"abcdefghij\"", "10"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"] + ] + }, + { + "params": ["2", "\"abcdefghijk\"", "11"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "206b"] + ] + }, + { + "params": ["2", "\"abcdefghijkl\"", "12"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"] + ] + }, + { + "params": ["2", "\"abcdefghijklm\"", "13"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "206d"] + ] + }, + { + "params": ["2", "\"abcdefghijklmn\"", "14"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "6e6d"] + ] + }, + { + "params": ["2", "\"abcdefghijklmno\"", "15"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "6e6d"], + ["00d4", "206f"] + ] + }, + { + "params": ["2", "\"abcdefghijklmnop\"", "16"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "6e6d"], + ["00d4", "706f"] + ] + }, + { + "params": ["2", "\"abcdefghijklmnopq\"", "17"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "6e6d"], + ["00d4", "706f"] + ] + }, + { + "params": ["2", "\"abcdefghijklmnopqr\"", "18"], + "output": [ + ["00dc", "0000"], + ["00d4", "6261"], + ["00d4", "6463"], + ["00d4", "6665"], + ["00d4", "6867"], + ["00d4", "6a69"], + ["00d4", "6c6b"], + ["00d4", "6e6d"], + ["00d4", "706f"] + ] + }, + { + "params": ["3", "\"\"", "0"], + "retval": "INVALID_PARAM" + } + ] + }, + "Brightness": { + "function": "libx52_set_brightness", + "tests": [ + { + "params": ["0", "0"], + "output": [["00b2", "0000"]] + }, + { + "params": ["0", "1"], + "output": [["00b2", "0001"]] + }, + { + "params": ["0", "2"], + "output": [["00b2", "0002"]] + }, + { + "params": ["0", "3"], + "output": [["00b2", "0003"]] + }, + { + "params": ["0", "4"], + "output": [["00b2", "0004"]] + }, + { + "params": ["0", "5"], + "output": [["00b2", "0005"]] + }, + { + "params": ["0", "6"], + "output": [["00b2", "0006"]] + }, + { + "params": ["0", "7"], + "output": [["00b2", "0007"]] + }, + { + "params": ["0", "8"], + "output": [["00b2", "0008"]] + }, + { + "params": ["0", "9"], + "output": [["00b2", "0009"]] + }, + { + "params": ["0", "10"], + "output": [["00b2", "000a"]] + }, + { + "params": ["0", "11"], + "output": [["00b2", "000b"]] + }, + { + "params": ["0", "12"], + "output": [["00b2", "000c"]] + }, + { + "params": ["0", "13"], + "output": [["00b2", "000d"]] + }, + { + "params": ["0", "14"], + "output": [["00b2", "000e"]] + }, + { + "params": ["0", "15"], + "output": [["00b2", "000f"]] + }, + { + "params": ["0", "16"], + "output": [["00b2", "0010"]] + }, + { + "params": ["0", "17"], + "output": [["00b2", "0011"]] + }, + { + "params": ["0", "18"], + "output": [["00b2", "0012"]] + }, + { + "params": ["0", "19"], + "output": [["00b2", "0013"]] + }, + { + "params": ["0", "20"], + "output": [["00b2", "0014"]] + }, + { + "params": ["0", "21"], + "output": [["00b2", "0015"]] + }, + { + "params": ["0", "22"], + "output": [["00b2", "0016"]] + }, + { + "params": ["0", "23"], + "output": [["00b2", "0017"]] + }, + { + "params": ["0", "24"], + "output": [["00b2", "0018"]] + }, + { + "params": ["0", "25"], + "output": [["00b2", "0019"]] + }, + { + "params": ["0", "26"], + "output": [["00b2", "001a"]] + }, + { + "params": ["0", "27"], + "output": [["00b2", "001b"]] + }, + { + "params": ["0", "28"], + "output": [["00b2", "001c"]] + }, + { + "params": ["0", "29"], + "output": [["00b2", "001d"]] + }, + { + "params": ["0", "30"], + "output": [["00b2", "001e"]] + }, + { + "params": ["0", "31"], + "output": [["00b2", "001f"]] + }, + { + "params": ["0", "32"], + "output": [["00b2", "0020"]] + }, + { + "params": ["0", "33"], + "output": [["00b2", "0021"]] + }, + { + "params": ["0", "34"], + "output": [["00b2", "0022"]] + }, + { + "params": ["0", "35"], + "output": [["00b2", "0023"]] + }, + { + "params": ["0", "36"], + "output": [["00b2", "0024"]] + }, + { + "params": ["0", "37"], + "output": [["00b2", "0025"]] + }, + { + "params": ["0", "38"], + "output": [["00b2", "0026"]] + }, + { + "params": ["0", "39"], + "output": [["00b2", "0027"]] + }, + { + "params": ["0", "40"], + "output": [["00b2", "0028"]] + }, + { + "params": ["0", "41"], + "output": [["00b2", "0029"]] + }, + { + "params": ["0", "42"], + "output": [["00b2", "002a"]] + }, + { + "params": ["0", "43"], + "output": [["00b2", "002b"]] + }, + { + "params": ["0", "44"], + "output": [["00b2", "002c"]] + }, + { + "params": ["0", "45"], + "output": [["00b2", "002d"]] + }, + { + "params": ["0", "46"], + "output": [["00b2", "002e"]] + }, + { + "params": ["0", "47"], + "output": [["00b2", "002f"]] + }, + { + "params": ["0", "48"], + "output": [["00b2", "0030"]] + }, + { + "params": ["0", "49"], + "output": [["00b2", "0031"]] + }, + { + "params": ["0", "50"], + "output": [["00b2", "0032"]] + }, + { + "params": ["0", "51"], + "output": [["00b2", "0033"]] + }, + { + "params": ["0", "52"], + "output": [["00b2", "0034"]] + }, + { + "params": ["0", "53"], + "output": [["00b2", "0035"]] + }, + { + "params": ["0", "54"], + "output": [["00b2", "0036"]] + }, + { + "params": ["0", "55"], + "output": [["00b2", "0037"]] + }, + { + "params": ["0", "56"], + "output": [["00b2", "0038"]] + }, + { + "params": ["0", "57"], + "output": [["00b2", "0039"]] + }, + { + "params": ["0", "58"], + "output": [["00b2", "003a"]] + }, + { + "params": ["0", "59"], + "output": [["00b2", "003b"]] + }, + { + "params": ["0", "60"], + "output": [["00b2", "003c"]] + }, + { + "params": ["0", "61"], + "output": [["00b2", "003d"]] + }, + { + "params": ["0", "62"], + "output": [["00b2", "003e"]] + }, + { + "params": ["0", "63"], + "output": [["00b2", "003f"]] + }, + { + "params": ["0", "64"], + "output": [["00b2", "0040"]] + }, + { + "params": ["0", "65"], + "output": [["00b2", "0041"]] + }, + { + "params": ["0", "66"], + "output": [["00b2", "0042"]] + }, + { + "params": ["0", "67"], + "output": [["00b2", "0043"]] + }, + { + "params": ["0", "68"], + "output": [["00b2", "0044"]] + }, + { + "params": ["0", "69"], + "output": [["00b2", "0045"]] + }, + { + "params": ["0", "70"], + "output": [["00b2", "0046"]] + }, + { + "params": ["0", "71"], + "output": [["00b2", "0047"]] + }, + { + "params": ["0", "72"], + "output": [["00b2", "0048"]] + }, + { + "params": ["0", "73"], + "output": [["00b2", "0049"]] + }, + { + "params": ["0", "74"], + "output": [["00b2", "004a"]] + }, + { + "params": ["0", "75"], + "output": [["00b2", "004b"]] + }, + { + "params": ["0", "76"], + "output": [["00b2", "004c"]] + }, + { + "params": ["0", "77"], + "output": [["00b2", "004d"]] + }, + { + "params": ["0", "78"], + "output": [["00b2", "004e"]] + }, + { + "params": ["0", "79"], + "output": [["00b2", "004f"]] + }, + { + "params": ["0", "80"], + "output": [["00b2", "0050"]] + }, + { + "params": ["0", "81"], + "output": [["00b2", "0051"]] + }, + { + "params": ["0", "82"], + "output": [["00b2", "0052"]] + }, + { + "params": ["0", "83"], + "output": [["00b2", "0053"]] + }, + { + "params": ["0", "84"], + "output": [["00b2", "0054"]] + }, + { + "params": ["0", "85"], + "output": [["00b2", "0055"]] + }, + { + "params": ["0", "86"], + "output": [["00b2", "0056"]] + }, + { + "params": ["0", "87"], + "output": [["00b2", "0057"]] + }, + { + "params": ["0", "88"], + "output": [["00b2", "0058"]] + }, + { + "params": ["0", "89"], + "output": [["00b2", "0059"]] + }, + { + "params": ["0", "90"], + "output": [["00b2", "005a"]] + }, + { + "params": ["0", "91"], + "output": [["00b2", "005b"]] + }, + { + "params": ["0", "92"], + "output": [["00b2", "005c"]] + }, + { + "params": ["0", "93"], + "output": [["00b2", "005d"]] + }, + { + "params": ["0", "94"], + "output": [["00b2", "005e"]] + }, + { + "params": ["0", "95"], + "output": [["00b2", "005f"]] + }, + { + "params": ["0", "96"], + "output": [["00b2", "0060"]] + }, + { + "params": ["0", "97"], + "output": [["00b2", "0061"]] + }, + { + "params": ["0", "98"], + "output": [["00b2", "0062"]] + }, + { + "params": ["0", "99"], + "output": [["00b2", "0063"]] + }, + { + "params": ["0", "100"], + "output": [["00b2", "0064"]] + }, + { + "params": ["0", "101"], + "output": [["00b2", "0065"]] + }, + { + "params": ["0", "102"], + "output": [["00b2", "0066"]] + }, + { + "params": ["0", "103"], + "output": [["00b2", "0067"]] + }, + { + "params": ["0", "104"], + "output": [["00b2", "0068"]] + }, + { + "params": ["0", "105"], + "output": [["00b2", "0069"]] + }, + { + "params": ["0", "106"], + "output": [["00b2", "006a"]] + }, + { + "params": ["0", "107"], + "output": [["00b2", "006b"]] + }, + { + "params": ["0", "108"], + "output": [["00b2", "006c"]] + }, + { + "params": ["0", "109"], + "output": [["00b2", "006d"]] + }, + { + "params": ["0", "110"], + "output": [["00b2", "006e"]] + }, + { + "params": ["0", "111"], + "output": [["00b2", "006f"]] + }, + { + "params": ["0", "112"], + "output": [["00b2", "0070"]] + }, + { + "params": ["0", "113"], + "output": [["00b2", "0071"]] + }, + { + "params": ["0", "114"], + "output": [["00b2", "0072"]] + }, + { + "params": ["0", "115"], + "output": [["00b2", "0073"]] + }, + { + "params": ["0", "116"], + "output": [["00b2", "0074"]] + }, + { + "params": ["0", "117"], + "output": [["00b2", "0075"]] + }, + { + "params": ["0", "118"], + "output": [["00b2", "0076"]] + }, + { + "params": ["0", "119"], + "output": [["00b2", "0077"]] + }, + { + "params": ["0", "120"], + "output": [["00b2", "0078"]] + }, + { + "params": ["0", "121"], + "output": [["00b2", "0079"]] + }, + { + "params": ["0", "122"], + "output": [["00b2", "007a"]] + }, + { + "params": ["0", "123"], + "output": [["00b2", "007b"]] + }, + { + "params": ["0", "124"], + "output": [["00b2", "007c"]] + }, + { + "params": ["0", "125"], + "output": [["00b2", "007d"]] + }, + { + "params": ["0", "126"], + "output": [["00b2", "007e"]] + }, + { + "params": ["0", "127"], + "output": [["00b2", "007f"]] + }, + { + "params": ["0", "128"], + "output": [["00b2", "0080"]] + }, + { + "params": ["1", "0"], + "output": [["00b1", "0000"]] + }, + { + "params": ["1", "1"], + "output": [["00b1", "0001"]] + }, + { + "params": ["1", "2"], + "output": [["00b1", "0002"]] + }, + { + "params": ["1", "3"], + "output": [["00b1", "0003"]] + }, + { + "params": ["1", "4"], + "output": [["00b1", "0004"]] + }, + { + "params": ["1", "5"], + "output": [["00b1", "0005"]] + }, + { + "params": ["1", "6"], + "output": [["00b1", "0006"]] + }, + { + "params": ["1", "7"], + "output": [["00b1", "0007"]] + }, + { + "params": ["1", "8"], + "output": [["00b1", "0008"]] + }, + { + "params": ["1", "9"], + "output": [["00b1", "0009"]] + }, + { + "params": ["1", "10"], + "output": [["00b1", "000a"]] + }, + { + "params": ["1", "11"], + "output": [["00b1", "000b"]] + }, + { + "params": ["1", "12"], + "output": [["00b1", "000c"]] + }, + { + "params": ["1", "13"], + "output": [["00b1", "000d"]] + }, + { + "params": ["1", "14"], + "output": [["00b1", "000e"]] + }, + { + "params": ["1", "15"], + "output": [["00b1", "000f"]] + }, + { + "params": ["1", "16"], + "output": [["00b1", "0010"]] + }, + { + "params": ["1", "17"], + "output": [["00b1", "0011"]] + }, + { + "params": ["1", "18"], + "output": [["00b1", "0012"]] + }, + { + "params": ["1", "19"], + "output": [["00b1", "0013"]] + }, + { + "params": ["1", "20"], + "output": [["00b1", "0014"]] + }, + { + "params": ["1", "21"], + "output": [["00b1", "0015"]] + }, + { + "params": ["1", "22"], + "output": [["00b1", "0016"]] + }, + { + "params": ["1", "23"], + "output": [["00b1", "0017"]] + }, + { + "params": ["1", "24"], + "output": [["00b1", "0018"]] + }, + { + "params": ["1", "25"], + "output": [["00b1", "0019"]] + }, + { + "params": ["1", "26"], + "output": [["00b1", "001a"]] + }, + { + "params": ["1", "27"], + "output": [["00b1", "001b"]] + }, + { + "params": ["1", "28"], + "output": [["00b1", "001c"]] + }, + { + "params": ["1", "29"], + "output": [["00b1", "001d"]] + }, + { + "params": ["1", "30"], + "output": [["00b1", "001e"]] + }, + { + "params": ["1", "31"], + "output": [["00b1", "001f"]] + }, + { + "params": ["1", "32"], + "output": [["00b1", "0020"]] + }, + { + "params": ["1", "33"], + "output": [["00b1", "0021"]] + }, + { + "params": ["1", "34"], + "output": [["00b1", "0022"]] + }, + { + "params": ["1", "35"], + "output": [["00b1", "0023"]] + }, + { + "params": ["1", "36"], + "output": [["00b1", "0024"]] + }, + { + "params": ["1", "37"], + "output": [["00b1", "0025"]] + }, + { + "params": ["1", "38"], + "output": [["00b1", "0026"]] + }, + { + "params": ["1", "39"], + "output": [["00b1", "0027"]] + }, + { + "params": ["1", "40"], + "output": [["00b1", "0028"]] + }, + { + "params": ["1", "41"], + "output": [["00b1", "0029"]] + }, + { + "params": ["1", "42"], + "output": [["00b1", "002a"]] + }, + { + "params": ["1", "43"], + "output": [["00b1", "002b"]] + }, + { + "params": ["1", "44"], + "output": [["00b1", "002c"]] + }, + { + "params": ["1", "45"], + "output": [["00b1", "002d"]] + }, + { + "params": ["1", "46"], + "output": [["00b1", "002e"]] + }, + { + "params": ["1", "47"], + "output": [["00b1", "002f"]] + }, + { + "params": ["1", "48"], + "output": [["00b1", "0030"]] + }, + { + "params": ["1", "49"], + "output": [["00b1", "0031"]] + }, + { + "params": ["1", "50"], + "output": [["00b1", "0032"]] + }, + { + "params": ["1", "51"], + "output": [["00b1", "0033"]] + }, + { + "params": ["1", "52"], + "output": [["00b1", "0034"]] + }, + { + "params": ["1", "53"], + "output": [["00b1", "0035"]] + }, + { + "params": ["1", "54"], + "output": [["00b1", "0036"]] + }, + { + "params": ["1", "55"], + "output": [["00b1", "0037"]] + }, + { + "params": ["1", "56"], + "output": [["00b1", "0038"]] + }, + { + "params": ["1", "57"], + "output": [["00b1", "0039"]] + }, + { + "params": ["1", "58"], + "output": [["00b1", "003a"]] + }, + { + "params": ["1", "59"], + "output": [["00b1", "003b"]] + }, + { + "params": ["1", "60"], + "output": [["00b1", "003c"]] + }, + { + "params": ["1", "61"], + "output": [["00b1", "003d"]] + }, + { + "params": ["1", "62"], + "output": [["00b1", "003e"]] + }, + { + "params": ["1", "63"], + "output": [["00b1", "003f"]] + }, + { + "params": ["1", "64"], + "output": [["00b1", "0040"]] + }, + { + "params": ["1", "65"], + "output": [["00b1", "0041"]] + }, + { + "params": ["1", "66"], + "output": [["00b1", "0042"]] + }, + { + "params": ["1", "67"], + "output": [["00b1", "0043"]] + }, + { + "params": ["1", "68"], + "output": [["00b1", "0044"]] + }, + { + "params": ["1", "69"], + "output": [["00b1", "0045"]] + }, + { + "params": ["1", "70"], + "output": [["00b1", "0046"]] + }, + { + "params": ["1", "71"], + "output": [["00b1", "0047"]] + }, + { + "params": ["1", "72"], + "output": [["00b1", "0048"]] + }, + { + "params": ["1", "73"], + "output": [["00b1", "0049"]] + }, + { + "params": ["1", "74"], + "output": [["00b1", "004a"]] + }, + { + "params": ["1", "75"], + "output": [["00b1", "004b"]] + }, + { + "params": ["1", "76"], + "output": [["00b1", "004c"]] + }, + { + "params": ["1", "77"], + "output": [["00b1", "004d"]] + }, + { + "params": ["1", "78"], + "output": [["00b1", "004e"]] + }, + { + "params": ["1", "79"], + "output": [["00b1", "004f"]] + }, + { + "params": ["1", "80"], + "output": [["00b1", "0050"]] + }, + { + "params": ["1", "81"], + "output": [["00b1", "0051"]] + }, + { + "params": ["1", "82"], + "output": [["00b1", "0052"]] + }, + { + "params": ["1", "83"], + "output": [["00b1", "0053"]] + }, + { + "params": ["1", "84"], + "output": [["00b1", "0054"]] + }, + { + "params": ["1", "85"], + "output": [["00b1", "0055"]] + }, + { + "params": ["1", "86"], + "output": [["00b1", "0056"]] + }, + { + "params": ["1", "87"], + "output": [["00b1", "0057"]] + }, + { + "params": ["1", "88"], + "output": [["00b1", "0058"]] + }, + { + "params": ["1", "89"], + "output": [["00b1", "0059"]] + }, + { + "params": ["1", "90"], + "output": [["00b1", "005a"]] + }, + { + "params": ["1", "91"], + "output": [["00b1", "005b"]] + }, + { + "params": ["1", "92"], + "output": [["00b1", "005c"]] + }, + { + "params": ["1", "93"], + "output": [["00b1", "005d"]] + }, + { + "params": ["1", "94"], + "output": [["00b1", "005e"]] + }, + { + "params": ["1", "95"], + "output": [["00b1", "005f"]] + }, + { + "params": ["1", "96"], + "output": [["00b1", "0060"]] + }, + { + "params": ["1", "97"], + "output": [["00b1", "0061"]] + }, + { + "params": ["1", "98"], + "output": [["00b1", "0062"]] + }, + { + "params": ["1", "99"], + "output": [["00b1", "0063"]] + }, + { + "params": ["1", "100"], + "output": [["00b1", "0064"]] + }, + { + "params": ["1", "101"], + "output": [["00b1", "0065"]] + }, + { + "params": ["1", "102"], + "output": [["00b1", "0066"]] + }, + { + "params": ["1", "103"], + "output": [["00b1", "0067"]] + }, + { + "params": ["1", "104"], + "output": [["00b1", "0068"]] + }, + { + "params": ["1", "105"], + "output": [["00b1", "0069"]] + }, + { + "params": ["1", "106"], + "output": [["00b1", "006a"]] + }, + { + "params": ["1", "107"], + "output": [["00b1", "006b"]] + }, + { + "params": ["1", "108"], + "output": [["00b1", "006c"]] + }, + { + "params": ["1", "109"], + "output": [["00b1", "006d"]] + }, + { + "params": ["1", "110"], + "output": [["00b1", "006e"]] + }, + { + "params": ["1", "111"], + "output": [["00b1", "006f"]] + }, + { + "params": ["1", "112"], + "output": [["00b1", "0070"]] + }, + { + "params": ["1", "113"], + "output": [["00b1", "0071"]] + }, + { + "params": ["1", "114"], + "output": [["00b1", "0072"]] + }, + { + "params": ["1", "115"], + "output": [["00b1", "0073"]] + }, + { + "params": ["1", "116"], + "output": [["00b1", "0074"]] + }, + { + "params": ["1", "117"], + "output": [["00b1", "0075"]] + }, + { + "params": ["1", "118"], + "output": [["00b1", "0076"]] + }, + { + "params": ["1", "119"], + "output": [["00b1", "0077"]] + }, + { + "params": ["1", "120"], + "output": [["00b1", "0078"]] + }, + { + "params": ["1", "121"], + "output": [["00b1", "0079"]] + }, + { + "params": ["1", "122"], + "output": [["00b1", "007a"]] + }, + { + "params": ["1", "123"], + "output": [["00b1", "007b"]] + }, + { + "params": ["1", "124"], + "output": [["00b1", "007c"]] + }, + { + "params": ["1", "125"], + "output": [["00b1", "007d"]] + }, + { + "params": ["1", "126"], + "output": [["00b1", "007e"]] + }, + { + "params": ["1", "127"], + "output": [["00b1", "007f"]] + }, + { + "params": ["1", "128"], + "output": [["00b1", "0080"]] + } + ] + }, + "Blink": { + "function": "libx52_set_blink", + "tests": [ + {"params": ["0"], "output": [["00b4", "0050"]]}, + {"params": ["1"], "output": [["00b4", "0051"]]} + ] + }, + "Shift": { + "function": "libx52_set_shift", + "tests": [ + {"params": ["0"], "output": [["00fd", "0050"]]}, + {"params": ["1"], "output": [["00fd", "0051"]]} + ] + }, + "Time": { + "function": "libx52_set_time", + "tests": [ + {"params": ["0", "0"], "output": [["00c0", "0000"]]}, + {"params": ["0", "1"], "output": [["00c0", "0001"]]}, + {"params": ["0", "2"], "output": [["00c0", "0002"]]}, + {"params": ["1", "0"], "output": [["00c0", "0100"]]}, + {"params": ["1", "1"], "output": [["00c0", "0101"]]}, + {"params": ["1", "2"], "output": [["00c0", "0102"]]}, + {"params": ["2", "0"], "output": [["00c0", "0200"]]}, + {"params": ["2", "1"], "output": [["00c0", "0201"]]}, + {"params": ["2", "2"], "output": [["00c0", "0202"]]} + ] + }, + "Time_Format": { + "function": "libx52_set_clock_format", + "params_prefix": ["LIBX52_CLOCK_", "LIBX52_CLOCK_FORMAT_"], + "tests": [ + {"params": ["1", "12HR"], "output": [["00c0", "0000"]]}, + {"params": ["1", "24HR"], "output": [["00c0", "8000"]]}, + {"params": ["2", "12HR"], "output": [["00c1", "0000"]]}, + {"params": ["2", "24HR"], "output": [["00c1", "8000"]]}, + {"params": ["3", "12HR"], "output": [["00c2", "0000"]]}, + {"params": ["3", "24HR"], "output": [["00c2", "8000"]]} + ] + }, + "Offset": { + "function": "libx52_set_clock_timezone", + "params_prefix": ["LIBX52_CLOCK_"], + "tests": [ + {"params": ["1", "0"], "retval": "NOT_SUPPORTED"}, + {"params": ["2", "0"], "output": [["00c1", "0000"]]}, + {"params": ["2", "30"], "output": [["00c1", "001e"]]}, + {"params": ["2", "60"], "output": [["00c1", "003c"]]}, + {"params": ["2", "1200"], "output": [["00c1", "04f0"]]}, + {"params": ["2", "1440"], "output": [["00c1", "0000"]]}, + {"params": ["2", "1441"], "retval": "OUT_OF_RANGE"}, + {"params": ["2", "-30"], "output": [["00c1", "041e"]]}, + {"params": ["2", "-60"], "output": [["00c1", "043c"]]}, + {"params": ["2", "-1200"], "output": [["00c1", "00f0"]]}, + {"params": ["2", "-1440"], "output": [["00c1", "0400"]]}, + {"params": ["2", "-1441"], "retval": "OUT_OF_RANGE"}, + {"params": ["3", "0"], "output": [["00c2", "0000"]]}, + {"params": ["3", "30"], "output": [["00c2", "001e"]]}, + {"params": ["3", "60"], "output": [["00c2", "003c"]]}, + {"params": ["3", "1200"], "output": [["00c2", "04f0"]]}, + {"params": ["3", "1440"], "output": [["00c2", "0000"]]}, + {"params": ["3", "1441"], "retval": "OUT_OF_RANGE"}, + {"params": ["3", "-30"], "output": [["00c2", "041e"]]}, + {"params": ["3", "-60"], "output": [["00c2", "043c"]]}, + {"params": ["3", "-1200"], "output": [["00c2", "00f0"]]}, + {"params": ["3", "-1440"], "output": [["00c2", "0400"]]}, + {"params": ["3", "-1441"], "retval": "OUT_OF_RANGE"} + ] + }, + "Date_Format": { + "function": "libx52_set_date_format", + "params_prefix": ["LIBX52_DATE_FORMAT_"], + "setup_hook": [ + "libx52_set_date(dev, 1, 2, 3);" + ], + "tests": [ + {"params": ["DDMMYY"], "output": [["00c4", "0201"], ["00c8", "0003"]]}, + {"params": ["MMDDYY"], "output": [["00c4", "0102"], ["00c8", "0003"]]}, + {"params": ["YYMMDD"], "output": [["00c4", "0203"], ["00c8", "0001"]]} + ] + }, + "Clock": { + "function": "libx52_set_clock", + "setup_hook": [ + "putenv(\"TZ=America/Los_Angeles\");" + ], + "tests": [ + { + "_comment": "2020-06-01 15:04:05 PDT", + "params": ["1591049045", "1"], + "output": [ + ["00c4", "0601"], + ["00c8", "0014"], + ["00c0", "0f04"], + ["00c1", "01a4"], + ["00c2", "01a4"] + ] + }, + { + "_comment": "2020-06-01 22:04:05 UTC", + "params": ["1591049045", "0"], + "output": [ + ["00c4", "0601"], + ["00c8", "0014"], + ["00c0", "1604"] + ] + }, + + { + "_comment": "2020-03-01 15:04:05 PST", + "params": ["1583103845", "1"], + "output": [ + ["00c4", "0301"], + ["00c8", "0014"], + ["00c0", "0f04"], + ["00c1", "01e0"], + ["00c2", "01e0"] + ] + }, + { + "_comment": "2020-03-01 23:04:05 UTC", + "params": ["1583103845", "0"], + "output": [ + ["00c4", "0301"], + ["00c8", "0014"], + ["00c0", "1704"] + ] + } + ] + } +} +