Move the code from the touchpad code into the more generic evdev code Signed-off-by: Peter Hutterer <peter.hutte...@who-t.net> --- src/evdev-mt-touchpad.c | 76 +++++++++---------------------------------------- src/evdev-mt-touchpad.h | 5 ---- src/evdev.c | 6 ++++ src/evdev.h | 65 ++++++++++++++++++++++++++++++++++++++++++ test/log.c | 50 ++++++++++++++++++++++++++++++++ 5 files changed, 134 insertions(+), 68 deletions(-)
diff --git a/src/evdev-mt-touchpad.c b/src/evdev-mt-touchpad.c index 7b8514c..0492851 100644 --- a/src/evdev-mt-touchpad.c +++ b/src/evdev-mt-touchpad.c @@ -279,39 +279,6 @@ tp_get_delta(struct tp_touch *t) return tp_normalize_delta(t->tp, delta); } -static inline void -tp_check_axis_range(struct tp_dispatch *tp, - unsigned int code, - int value) -{ - int min, max; - - switch(code) { - case ABS_X: - case ABS_MT_POSITION_X: - min = tp->warning_range.min.x; - max = tp->warning_range.max.x; - break; - case ABS_Y: - case ABS_MT_POSITION_Y: - min = tp->warning_range.min.y; - max = tp->warning_range.max.y; - break; - default: - return; - } - - if (value < min || value > max) { - log_info_ratelimit(tp_libinput_context(tp), - &tp->warning_range.range_warn_limit, - "Axis %#x value %d is outside expected range [%d, %d]\n" - "See %s/absolute_coordinate_ranges.html for details\n", - code, value, min, max, - HTTP_DOC_LINK); - - } -} - static void tp_process_absolute(struct tp_dispatch *tp, const struct input_event *e, @@ -321,14 +288,18 @@ tp_process_absolute(struct tp_dispatch *tp, switch(e->code) { case ABS_MT_POSITION_X: - tp_check_axis_range(tp, e->code, e->value); + evdev_device_check_abs_axis_range(tp->device, + e->code, + e->value); t->point.x = e->value; t->millis = time; t->dirty = true; tp->queued |= TOUCHPAD_EVENT_MOTION; break; case ABS_MT_POSITION_Y: - tp_check_axis_range(tp, e->code, e->value); + evdev_device_check_abs_axis_range(tp->device, + e->code, + e->value); t->point.y = e->value; t->millis = time; t->dirty = true; @@ -363,14 +334,18 @@ tp_process_absolute_st(struct tp_dispatch *tp, switch(e->code) { case ABS_X: - tp_check_axis_range(tp, e->code, e->value); + evdev_device_check_abs_axis_range(tp->device, + e->code, + e->value); t->point.x = e->value; t->millis = time; t->dirty = true; tp->queued |= TOUCHPAD_EVENT_MOTION; break; case ABS_Y: - tp_check_axis_range(tp, e->code, e->value); + evdev_device_check_abs_axis_range(tp->device, + e->code, + e->value); t->point.y = e->value; t->millis = time; t->dirty = true; @@ -2241,32 +2216,10 @@ tp_init_hysteresis(struct tp_dispatch *tp) return; } -static void -tp_init_range_warnings(struct tp_dispatch *tp, - struct evdev_device *device, - int width, - int height) -{ - const struct input_absinfo *x, *y; - - x = device->abs.absinfo_x; - y = device->abs.absinfo_y; - - tp->warning_range.min.x = x->minimum - 0.05 * width; - tp->warning_range.min.y = y->minimum - 0.05 * height; - tp->warning_range.max.x = x->maximum + 0.05 * width; - tp->warning_range.max.y = y->maximum + 0.05 * height; - - /* One warning every 5 min is enough */ - ratelimit_init(&tp->warning_range.range_warn_limit, s2us(3000), 1); -} - static int tp_init(struct tp_dispatch *tp, struct evdev_device *device) { - int width, height; - tp->base.interface = &tp_interface; tp->device = device; @@ -2278,10 +2231,7 @@ tp_init(struct tp_dispatch *tp, if (!tp_init_slots(tp, device)) return false; - width = device->abs.dimensions.x; - height = device->abs.dimensions.y; - - tp_init_range_warnings(tp, device, width, height); + evdev_device_init_abs_range_warnings(device); tp->reports_distance = libevdev_has_event_code(device->evdev, EV_ABS, diff --git a/src/evdev-mt-touchpad.h b/src/evdev-mt-touchpad.h index f4ad090..db0a51a 100644 --- a/src/evdev-mt-touchpad.h +++ b/src/evdev-mt-touchpad.h @@ -248,11 +248,6 @@ struct tp_dispatch { struct device_coords hysteresis_margin; struct { - struct device_coords min, max; - struct ratelimit range_warn_limit; - } warning_range; - - struct { double x_scale_coeff; double y_scale_coeff; } accel; diff --git a/src/evdev.c b/src/evdev.c index 1e3cc90..afb5e34 100644 --- a/src/evdev.c +++ b/src/evdev.c @@ -852,11 +852,13 @@ fallback_process_touch(struct fallback_dispatch *dispatch, dispatch->pending_event = EVDEV_ABSOLUTE_MT_UP; break; case ABS_MT_POSITION_X: + evdev_device_check_abs_axis_range(device, e->code, e->value); dispatch->mt.slots[dispatch->mt.slot].point.x = e->value; if (dispatch->pending_event == EVDEV_NONE) dispatch->pending_event = EVDEV_ABSOLUTE_MT_MOTION; break; case ABS_MT_POSITION_Y: + evdev_device_check_abs_axis_range(device, e->code, e->value); dispatch->mt.slots[dispatch->mt.slot].point.y = e->value; if (dispatch->pending_event == EVDEV_NONE) dispatch->pending_event = EVDEV_ABSOLUTE_MT_MOTION; @@ -870,11 +872,13 @@ fallback_process_absolute_motion(struct fallback_dispatch *dispatch, { switch (e->code) { case ABS_X: + evdev_device_check_abs_axis_range(device, e->code, e->value); dispatch->abs.point.x = e->value; if (dispatch->pending_event == EVDEV_NONE) dispatch->pending_event = EVDEV_ABSOLUTE_MOTION; break; case ABS_Y: + evdev_device_check_abs_axis_range(device, e->code, e->value); dispatch->abs.point.y = e->value; if (dispatch->pending_event == EVDEV_NONE) dispatch->pending_event = EVDEV_ABSOLUTE_MOTION; @@ -1716,6 +1720,8 @@ fallback_dispatch_init_abs(struct fallback_dispatch *dispatch, dispatch->abs.point.x = device->abs.absinfo_x->value; dispatch->abs.point.y = device->abs.absinfo_y->value; dispatch->abs.seat_slot = -1; + + evdev_device_init_abs_range_warnings(device); } static struct evdev_dispatch * diff --git a/src/evdev.h b/src/evdev.h index 3ad385e..b5a54a2 100644 --- a/src/evdev.h +++ b/src/evdev.h @@ -162,6 +162,11 @@ struct evdev_device { struct matrix usermatrix; /* as supplied by the caller */ struct device_coords dimensions; + + struct { + struct device_coords min, max; + struct ratelimit range_warn_limit; + } warning_range; } abs; struct { @@ -298,6 +303,11 @@ struct fallback_dispatch { struct { struct device_coords point; int32_t seat_slot; + + struct { + struct device_coords min, max; + struct ratelimit range_warn_limit; + } warning_range; } abs; struct { @@ -639,4 +649,59 @@ evdev_device_mm_to_units(const struct evdev_device *device, return units; } + +static inline void +evdev_device_init_abs_range_warnings(struct evdev_device *device) +{ + const struct input_absinfo *x, *y; + int width, height; + + x = device->abs.absinfo_x; + y = device->abs.absinfo_y; + width = device->abs.dimensions.x; + height = device->abs.dimensions.y; + + device->abs.warning_range.min.x = x->minimum - 0.05 * width; + device->abs.warning_range.min.y = y->minimum - 0.05 * height; + device->abs.warning_range.max.x = x->maximum + 0.05 * width; + device->abs.warning_range.max.y = y->maximum + 0.05 * height; + + /* One warning every 5 min is enough */ + ratelimit_init(&device->abs.warning_range.range_warn_limit, + s2us(3000), + 1); +} + +static inline void +evdev_device_check_abs_axis_range(struct evdev_device *device, + unsigned int code, + int value) +{ + int min, max; + + switch(code) { + case ABS_X: + case ABS_MT_POSITION_X: + min = device->abs.warning_range.min.x; + max = device->abs.warning_range.max.x; + break; + case ABS_Y: + case ABS_MT_POSITION_Y: + min = device->abs.warning_range.min.y; + max = device->abs.warning_range.max.y; + break; + default: + return; + } + + if (value < min || value > max) { + log_info_ratelimit(evdev_libinput_context(device), + &device->abs.warning_range.range_warn_limit, + "Axis %#x value %d is outside expected range [%d, %d]\n" + "See %s/absolute_coordinate_ranges.html for details\n", + code, value, min, max, + HTTP_DOC_LINK); + } +} + #endif /* EVDEV_H */ diff --git a/test/log.c b/test/log.c index 9dca152..9988267 100644 --- a/test/log.c +++ b/test/log.c @@ -140,11 +140,61 @@ START_TEST(log_priority) } END_TEST +static int axisrange_log_handler_called = 0; + +static void +axisrange_warning_log_handler(struct libinput *libinput, + enum libinput_log_priority priority, + const char *format, + va_list args) +{ + axisrange_log_handler_called++; + litest_assert_notnull(format); + litest_assert_notnull(strstr(format, "is outside expected range")); +} + +START_TEST(log_axisrange_warning) +{ + struct litest_device *dev = litest_current_device(); + struct libinput *li = dev->libinput; + const struct input_absinfo *abs; + int axis = _i; /* looped test */ + + litest_touch_down(dev, 0, 90, 100); + litest_drain_events(li); + + libinput_log_set_priority(li, LIBINPUT_LOG_PRIORITY_INFO); + libinput_log_set_handler(li, axisrange_warning_log_handler); + + abs = libevdev_get_abs_info(dev->evdev, axis); + + for (int i = 0; i < 100; i++) { + litest_event(dev, EV_ABS, + ABS_MT_POSITION_X + axis, + abs->maximum * 2 + i); + litest_event(dev, EV_ABS, axis, abs->maximum * 2); + litest_event(dev, EV_SYN, SYN_REPORT, 0); + libinput_dispatch(li); + } + + /* Expect only one message per 5 min */ + ck_assert_int_eq(axisrange_log_handler_called, 1); + + litest_restore_log_handler(li); + axisrange_log_handler_called = 0; +} +END_TEST + void litest_setup_tests_log(void) { + struct range axes = { ABS_X, ABS_Y + 1}; + litest_add_no_device("log:defaults", log_default_priority); litest_add_no_device("log:logging", log_handler_invoked); litest_add_no_device("log:logging", log_handler_NULL); litest_add_no_device("log:logging", log_priority); + + litest_add_ranged("log:warnings", log_axisrange_warning, LITEST_TOUCH, LITEST_ANY, &axes); + litest_add_ranged("log:warnings", log_axisrange_warning, LITEST_TOUCHPAD, LITEST_ANY, &axes); } -- 2.9.3 _______________________________________________ wayland-devel mailing list wayland-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/wayland-devel