diff --git a/test/Makefile.am b/test/Makefile.am index d8a6c86..578cbb7 100644 --- a/test/Makefile.am +++ b/test/Makefile.am @@ -1,4 +1,4 @@ -noinst_PROGRAMS = test-event-names test-libevdev-init +noinst_PROGRAMS = test-event-names test-libevdev-init test-libevdev-has-event TESTS = $(noinst_PROGRAMS) @@ -12,3 +12,6 @@ test_event_names_LDADD = $(libevdev_ldadd) $(CHECK_LIBS) test_libevdev_init_SOURCES = test-libevdev-init.c $(common_sources) test_libevdev_init_LDADD = $(libevdev_ldadd) $(CHECK_LIBS) + +test_libevdev_has_event_SOURCES = test-libevdev-has-event.c $(common_sources) +test_libevdev_has_event_LDADD = $(libevdev_ldadd) $(CHECK_LIBS) diff --git a/test/test-libevdev-has-event.c b/test/test-libevdev-has-event.c new file mode 100644 index 0000000..333dac8 --- /dev/null +++ b/test/test-libevdev-has-event.c @@ -0,0 +1,299 @@ +/* + * Copyright © 2013 Red Hat, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that copyright + * notice and this permission notice appear in supporting documentation, and + * that the name of the copyright holders not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. The copyright holders make no representations + * about the suitability of this software for any purpose. It is provided "as + * is" without express or implied warranty. + * + * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR + * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, + * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER + * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE + * OF THIS SOFTWARE. + */ + +#include +#include +#include + +#include +#include +#include +#include + +#include "test-common-uinput.h" + +static int evbits[] = { + EV_SYN, EV_KEY, EV_REL, EV_ABS, EV_MSC, + EV_SW, EV_LED, EV_SND, EV_FF, + /* Intentionally skipping these, they're different + * EV_PWR, EV_FF_STATUS, EV_REP, */ + -1, +}; + +START_TEST(test_has_ev_bit) +{ + int *evbit = evbits; + + while(*evbit != -1) { + struct uinput_device* uidev; + struct libevdev *dev; + int i, rc; + + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + *evbit, 0, + -1); + ck_assert_msg(rc == 0, "%s: Failed to create uinput device with: %s", + libevdev_get_event_type_name(*evbit), + strerror(-rc)); + rc = libevdev_new_from_fd(uinput_device_get_fd(uidev), &dev); + ck_assert_msg(rc == 0, "%s: Failed to init device: %s", + libevdev_get_event_type_name(*evbit), + strerror(-rc)); + + ck_assert_msg(libevdev_has_event_type(dev, EV_SYN), "for event type %d\n", *evbit); + ck_assert_msg(libevdev_has_event_type(dev, *evbit), "for event type %d\n", *evbit); + + for (i = 0; i <= EV_MAX; i++) { + if (i == EV_SYN || i == *evbit) + continue; + + ck_assert_msg(!libevdev_has_event_type(dev, i), "for event type %d\n", i); + } + + libevdev_free(dev); + uinput_device_free(uidev); + + evbit++; + } +} +END_TEST + +START_TEST(test_ev_bit_limits) +{ + int *evbit = evbits; + + while(*evbit != -1) { + struct uinput_device* uidev; + struct libevdev *dev; + int rc; + + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + *evbit, 0, + -1); + ck_assert_msg(rc == 0, "Failed to create uinput device: %s", strerror(-rc)); + rc = libevdev_new_from_fd(uinput_device_get_fd(uidev), &dev); + ck_assert_msg(rc == 0, "Failed to init device: %s", strerror(-rc));; + + ck_assert_int_eq(libevdev_has_event_type(dev, EV_MAX + 1), 0); + ck_assert_int_eq(libevdev_has_event_type(dev, INT_MAX), 0); + ck_assert_int_eq(libevdev_has_event_type(dev, UINT_MAX), 0); + + libevdev_free(dev); + uinput_device_free(uidev); + + evbit++; + } +} +END_TEST + +START_TEST(test_event_codes) +{ + int *evbit = evbits; + + while(*evbit != -1) { + struct uinput_device* uidev; + struct libevdev *dev; + int rc; + int code, max; + if (*evbit == EV_SYN) { + evbit++; + continue; + } + + max = libevdev_get_event_type_max(*evbit); + + for (code = 1; code < max; code += 10) { + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + *evbit, code, + -1); + ck_assert_msg(rc == 0, "Failed to create uinput device: %s", strerror(-rc)); + rc = libevdev_new_from_fd(uinput_device_get_fd(uidev), &dev); + ck_assert_msg(rc == 0, "Failed to init device: %s", strerror(-rc));; + + ck_assert_msg(libevdev_has_event_type(dev, *evbit), "for event type %d\n", *evbit); + ck_assert_msg(libevdev_has_event_code(dev, *evbit, code), "for type %d code %d", *evbit, code); + + libevdev_free(dev); + uinput_device_free(uidev); + } + + evbit++; + } +} +END_TEST + +START_TEST(test_event_code_limits) +{ + int *evbit = evbits; + + while(*evbit != -1) { + struct uinput_device* uidev; + struct libevdev *dev; + int rc; + int max; + + if (*evbit == EV_SYN) { + evbit++; + continue; + } + + max = libevdev_get_event_type_max(*evbit); + ck_assert(max != -1); + + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + *evbit, 1, + -1); + ck_assert_msg(rc == 0, "Failed to create uinput device: %s", strerror(-rc)); + rc = libevdev_new_from_fd(uinput_device_get_fd(uidev), &dev); + ck_assert_msg(rc == 0, "Failed to init device: %s", strerror(-rc));; + + ck_assert_msg(!libevdev_has_event_code(dev, *evbit, max), "for type %d code %d", *evbit, max); + ck_assert_msg(!libevdev_has_event_code(dev, *evbit, INT_MAX), "for type %d code %d", *evbit, INT_MAX); + ck_assert_msg(!libevdev_has_event_code(dev, *evbit, UINT_MAX), "for type %d code %d", *evbit, UINT_MAX); + + libevdev_free(dev); + uinput_device_free(uidev); + + evbit++; + } +} +END_TEST + +START_TEST(test_ev_rep) +{ + struct uinput_device* uidev; + int rc; + + /* EV_REP is special, it's always fully set if set at all, + can't test this through uinput though */ + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + EV_REP, 0, + -1); + ck_assert_int_eq(rc, -EINVAL); +} +END_TEST + +START_TEST(test_ev_rep_values) +{ + struct uinput_device* uidev; + struct libevdev *dev; + int rc; + int delay = 0xab, period = 0xbc; + + /* EV_REP is special, it's always fully set if set at all, can't set + it through uinput though. */ + rc = uinput_device_new_with_events(&uidev, "test device", DEFAULT_IDS, + -1); + ck_assert_msg(rc == 0, "Failed to create uinput device: %s", strerror(-rc)); + rc = libevdev_new_from_fd(uinput_device_get_fd(uidev), &dev); + ck_assert_msg(rc == 0, "Failed to init device: %s", strerror(-rc));; + + ck_assert_int_eq(libevdev_get_repeat(dev, NULL, NULL), -1); + ck_assert_int_eq(libevdev_get_repeat(dev, &delay, NULL), -1); + ck_assert_int_eq(libevdev_get_repeat(dev, NULL, &period), -1); + ck_assert_int_eq(libevdev_get_repeat(dev, &delay, &period), -1); + + ck_assert_int_eq(delay, 0xab); + ck_assert_int_eq(period, 0xbc); + + uinput_device_free(uidev); +} +END_TEST + +START_TEST(test_device_name) +{ + struct uinput_device* uidev; + struct libevdev *dev; + struct input_id ids = {1, 2, 3, 4}; + const char *str; + int rc; + + dev = libevdev_new(); + + str = libevdev_get_name(dev); + ck_assert(str != NULL); + ck_assert_int_eq(strlen(str), 0); + + rc = uinput_device_new_with_events(&uidev, "test device", &ids, + EV_ABS, ABS_X, + -1); + ck_assert_msg(rc == 0, "Failed to create uinput device: %s", strerror(-rc)); + rc = libevdev_set_fd(dev, uinput_device_get_fd(uidev)); + ck_assert_msg(rc == 0, "Failed to init device: %s", strerror(-rc));; + + str = libevdev_get_name(dev); + ck_assert_int_eq(strcmp(str, "test device"), 0); + + str = libevdev_get_phys(dev); + ck_assert(str == NULL); + + str = libevdev_get_uniq(dev); + ck_assert(str == NULL); + + ck_assert_int_eq(libevdev_get_bustype(dev), ids.bustype); + ck_assert_int_eq(libevdev_get_vendor_id(dev), ids.vendor); + ck_assert_int_eq(libevdev_get_product_id(dev), ids.product); + ck_assert_int_eq(libevdev_get_version(dev), ids.version); + ck_assert_int_eq(libevdev_get_driver_version(dev), EV_VERSION); + + uinput_device_free(uidev); +} +END_TEST + +Suite * +libevdev_has_event_test(void) +{ + Suite *s = suite_create("libevdev_has_event tests"); + + TCase *tc = tcase_create("event type"); + tcase_add_test(tc, test_ev_bit_limits); + tcase_add_test(tc, test_has_ev_bit); + suite_add_tcase(s, tc); + + tc = tcase_create("event codes"); + tcase_add_test(tc, test_event_codes); + tcase_add_test(tc, test_event_code_limits); + suite_add_tcase(s, tc); + + tc = tcase_create("ev_rep"); + tcase_add_test(tc, test_ev_rep); + tcase_add_test(tc, test_ev_rep_values); + suite_add_tcase(s, tc); + + tc = tcase_create("device info"); + tcase_add_test(tc, test_device_name); + suite_add_tcase(s, tc); + + return s; +} + +int main(int argc, char **argv) +{ + int failed; + Suite *s = libevdev_has_event_test(); + SRunner *sr = srunner_create(s); + srunner_run_all(sr, CK_NORMAL); + failed = srunner_ntests_failed(sr); + srunner_free(sr); + + return failed; +}