[PATCH 1/2] server: Split out varargs version of wl_resource_post_error.

2018-02-19 Thread raof
From: Christopher James Halse Rogers 

This will allow other wrappers around wl_resource_post_error to accept
variable argument lists.

Signed-off-by: Christopher James Halse Rogers 

---
 src/wayland-server.c | 23 ---
 1 file changed, 16 insertions(+), 7 deletions(-)

diff --git a/src/wayland-server.c b/src/wayland-server.c
index eb1e500..00c93f7 100644
--- a/src/wayland-server.c
+++ b/src/wayland-server.c
@@ -273,17 +273,14 @@ wl_resource_queue_event(struct wl_resource *resource, 
uint32_t opcode, ...)
wl_resource_queue_event_array(resource, opcode, args);
 }
 
-WL_EXPORT void
-wl_resource_post_error(struct wl_resource *resource,
-  uint32_t code, const char *msg, ...)
+static void
+wl_resource_post_error_vargs(struct wl_resource *resource,
+uint32_t code, const char *msg, va_list argp)
 {
struct wl_client *client = resource->client;
char buffer[128];
-   va_list ap;
 
-   va_start(ap, msg);
-   vsnprintf(buffer, sizeof buffer, msg, ap);
-   va_end(ap);
+   vsnprintf(buffer, sizeof buffer, msg, argp);
 
/*
 * When a client aborts, its resources are destroyed in id order,
@@ -298,6 +295,18 @@ wl_resource_post_error(struct wl_resource *resource,
wl_resource_post_event(client->display_resource,
   WL_DISPLAY_ERROR, resource, code, buffer);
client->error = 1;
+
+}
+
+WL_EXPORT void
+wl_resource_post_error(struct wl_resource *resource,
+  uint32_t code, const char *msg, ...)
+{
+   va_list ap;
+
+   va_start(ap, msg);
+   wl_resource_post_error_vargs(resource, code, msg, ap);
+   va_end(ap);
 }
 
 static void
-- 
2.15.1

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


RFC - Add internal server error message

2018-02-19 Thread raof
Because C++ exceptions escaping into C FFI invokes undefined behaviour
our Wayland implementation wraps all the interface vtable callbacks
with try {} catch (...) { log_error }.

This has the nice property of not crashing the server, but does result
in the client and server having different ideas about the current state.

In the interests of debugability it would be nice to tell clients that
their request failed due to server error rather than silently continue
into unknown territory.

These patches introduce a WL_DISPLAY_ERROR_INTERNAL error the compositor
can send in such cases.

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


[PATCH 2/2] proto, server: Add internal server error message.

2018-02-19 Thread raof
From: Christopher James Halse Rogers 

Many languages such as C++ or Rust have an unwinding error-reporting
mechanism. Code in these languages can (and must!) wrap request handling
callbacks in unwind guards to avoid undefined behaviour.

As a consequence such code will detect internal server errors, but have
no way to communicate such failures to the client.

This adds a WL_DISPLAY_ERROR_INTERNAL error to wl_display so that
such code can notify (and disconnect) client which hit internal bugs.

Signed-off-by: Christopher James Halse Rogers 

---
 protocol/wayland.xml  |  2 ++
 src/wayland-client.c  |  3 +++
 src/wayland-server-core.h |  4 
 src/wayland-server.c  | 23 +++
 tests/display-test.c  | 40 
 5 files changed, 72 insertions(+)

diff --git a/protocol/wayland.xml b/protocol/wayland.xml
index b5662e0..1db31a6 100644
--- a/protocol/wayland.xml
+++ b/protocol/wayland.xml
@@ -94,6 +94,8 @@
 summary="method doesn't exist on the specified interface"/>
   
+  
 
 
 
diff --git a/src/wayland-client.c b/src/wayland-client.c
index c1369b8..7c442b1 100644
--- a/src/wayland-client.c
+++ b/src/wayland-client.c
@@ -192,6 +192,9 @@ display_protocol_error(struct wl_display *display, uint32_t 
code,
case WL_DISPLAY_ERROR_NO_MEMORY:
err = ENOMEM;
break;
+   case WL_DISPLAY_ERROR_INTERNAL:
+   err = EPROTO;
+   break;
default:
err = EFAULT;
}
diff --git a/src/wayland-server-core.h b/src/wayland-server-core.h
index 2e725d9..7137da6 100644
--- a/src/wayland-server-core.h
+++ b/src/wayland-server-core.h
@@ -324,6 +324,10 @@ wl_client_get_object(struct wl_client *client, uint32_t 
id);
 void
 wl_client_post_no_memory(struct wl_client *client);
 
+void
+wl_client_post_internal_error(struct wl_client *client,
+ const char* msg, ...) WL_PRINTF(2,3);
+
 void
 wl_client_add_resource_created_listener(struct wl_client *client,
 struct wl_listener *listener);
diff --git a/src/wayland-server.c b/src/wayland-server.c
index 00c93f7..6317f8f 100644
--- a/src/wayland-server.c
+++ b/src/wayland-server.c
@@ -650,6 +650,29 @@ wl_client_post_no_memory(struct wl_client *client)
   WL_DISPLAY_ERROR_NO_MEMORY, "no memory");
 }
 
+/** Report an internal server error
+ *
+ * \param client The client object
+ * \param msg A printf-style format string
+ * \param ... Format string arguments
+ *
+ * Report an unspecified internal error and disconnect the client.
+ *
+ * \memberof wl_client
+ */
+WL_EXPORT void
+wl_client_post_internal_error(struct wl_client *client,
+ char const *msg, ...)
+{
+   va_list ap;
+
+   va_start(ap, msg);
+   wl_resource_post_error_vargs(client->display_resource,
+WL_DISPLAY_ERROR_INTERNAL,
+msg, ap);
+   va_end(ap);
+}
+
 WL_EXPORT void
 wl_resource_post_no_memory(struct wl_resource *resource)
 {
diff --git a/tests/display-test.c b/tests/display-test.c
index 9b49a0e..63f8b5a 100644
--- a/tests/display-test.c
+++ b/tests/display-test.c
@@ -419,6 +419,46 @@ TEST(post_nomem_tst)
display_destroy(d);
 }
 
+static void
+post_internal_error_main(void)
+{
+   struct client *c = client_connect();
+   struct wl_seat *seat = client_get_seat(c);
+   uint32_t object_id, protocol_error;
+   const struct wl_interface *interface;
+
+   assert(stop_display(c, 1) == -1);
+   int err = wl_display_get_error(c->wl_display);
+   fprintf(stderr, "Err is %i\n", err);
+   assert(err == EPROTO);
+   protocol_error = wl_display_get_protocol_error(c->wl_display,
+  &interface,
+  &object_id);
+   assert(protocol_error == WL_DISPLAY_ERROR_INTERNAL);
+   assert(interface == &wl_display_interface);
+
+   wl_proxy_destroy((struct wl_proxy *) seat);
+   client_disconnect_nocheck(c);
+}
+
+TEST(post_internal_error_tst)
+{
+   struct display *d = display_create();
+   struct client_info *cl;
+
+   wl_global_create(d->wl_display, &wl_seat_interface,
+1, d, bind_seat);
+
+   cl = client_create_noarg(d, post_internal_error_main);
+   display_run(d);
+
+   wl_client_post_internal_error(cl->wl_client, "Error %i", 20);
+
+   display_resume(d);
+
+   display_destroy(d);
+}
+
 static void
 register_reading(struct wl_display *display)
 {
-- 
2.15.1

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


Re: [PATCH v2] touchpad: add wobbling detection

2018-02-19 Thread Peter Hutterer
On Sun, Feb 18, 2018 at 11:14:55PM +0300, Konstantin Kharlamov wrote:
> The details are explained in comment in the code. That aside, I shall
> mention the check is so light, that it shouldn't influence CPU
> performance even a bit, and can blindly be kept always enabled.

I like it! And it does work with a change (see below), so provided it still
works for you, it's worth testing on more laptops.
 
> Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=104828
> 
> v2: rename the function, change comment style, and add calculation of
> x_diff (the one that was used is an absolute coordinate).
> 
> FWIW, the algorithm don't care that now added "prev_x" is unintialized,

prev_x is initialized to 0 because we calloc everything in libinput.

> because that happening means the time threshold won't get satisfied
> either. It's not like I can't default-init it — it's just that asking
> oneself a question "what default value should it have" results in "none".
> 
> Signed-off-by: Konstantin Kharlamov 
> ---
>  src/evdev-mt-touchpad.c | 33 +
>  src/evdev-mt-touchpad.h |  2 ++
>  2 files changed, 35 insertions(+)
> 
> diff --git a/src/evdev-mt-touchpad.c b/src/evdev-mt-touchpad.c
> index ead76456..80f56072 100644
> --- a/src/evdev-mt-touchpad.c
> +++ b/src/evdev-mt-touchpad.c
> @@ -131,6 +131,36 @@ tp_motion_history_push(struct tp_touch *t)
>   t->history.index = motion_index;
>  }
>  
> +static inline void
> +tp_detect_wobbling(struct tp_dispatch *tp, int x_diff, uint64_t time)
> +{
> + if (tp->hysteresis.enabled)
> + return;
> +
> + /* Idea: if we got a tuple of *very* quick moves like {Left, Right, 
> Left}, or
> +  * {Right, Left, Right}, it means touchpad jitters since no human 
> supposed to
> +  * be able to move like that within thresholds
> +  *
> +  * Algo: we encode left moves as zeroes, and right as ones. We also 
> drop the
> +  * array to all zeroes when contraints are not satisfied. Then we 
> search for
> +  * the pattern {1,0,1}. It can't match {Left, Right, Left}, but it does 
> match
> +  * {Left, Right, Left, Right}, so it's okay.
> +  */

the interesting bit here will be whether there are touchpads that wobble but
with more than one event per direction. I suspect there are but this should
be simple enough that it catches the first RLR movement (bound to happen at
some point) and enable it then. The main question is whether there is a
noticeable period of wobbling until this happens.
I honestly don't know, we won't know until ppl start shouting at us...

> + if (time - tp->hysteresis.last_motion_time > ms2us(20) || x_diff == 0) {
> + tp->hysteresis.x_motion_in_threshold = 0;
> + return;
> + }

empty line here please.

> + tp->hysteresis.x_motion_in_threshold <<= 1;
> + if (x_diff > 0) { /* right move */

s/x_diff/dx/, we use that everywhere else for deltas.

> + tp->hysteresis.x_motion_in_threshold |= 1;
> + static const char r_l_r = 5; /* {Right, Left, Right} */

declarations at the top of the block please, separated by an empty line. See
CODING_STYLE in the repository.

> + if (tp->hysteresis.x_motion_in_threshold & r_l_r) {

this one will trigger on the first right movement, you need
  if ((tp->hysteresis.x_motion_in_threshold & r_l_r) == r_l_r)

With that change, it seems to work correctly on my non-wobbling touchpad
here. Does it still work for you when you add this?

> + tp->hysteresis.enabled = true;
> + evdev_log_debug(tp->device, "hysteresis enabled\n");
> + }
> + }
> +}
> +
>  static inline void
>  tp_motion_hysteresis(struct tp_dispatch *tp,
>struct tp_touch *t)
> @@ -1405,6 +1435,8 @@ tp_process_state(struct tp_dispatch *tp, uint64_t time)
>   tp_thumb_detect(tp, t, time);
>   tp_palm_detect(tp, t, time);
>  
> + tp_detect_wobbling(tp, tp->hysteresis.prev_x - t->point.x, 
> time);
> + tp->hysteresis.prev_x = t->point.x;

the dx calculation should happen within tp_detect_wobbling, just pass the
touch in and do the subtraction there. Plus that way you can do a simple:
if (tp->prev.x == 0) dx = 0; 
which makes things more obvious.

>   tp_motion_hysteresis(tp, t);
>   tp_motion_history_push(t);
>  
> @@ -2918,6 +2950,7 @@ tp_init_hysteresis(struct tp_dispatch *tp)
>   tp->hysteresis.margin.x = res_x/2;
>   tp->hysteresis.margin.y = res_y/2;
>   tp->hysteresis.enabled = false;
> + tp->hysteresis.x_motion_in_threshold = 0;

'threshold' usually refers to a distance in libinput, here it's more a
timeout. But calling it x_motion_history would be best here, IMO.

>  }
>  
>  static void
> diff --git a/src/evdev-mt-touchpad.h b/src/evdev-mt-touchpad.h
> index 442f34a3..398a18ed 100644
> --- a/src/evdev-mt-touchpad.h
> +++ b/src/evdev-mt-touchpad.h
> @@ -276,6 +276,8 @

[PATCH libinput] touchpad: only begin fake touches when we have at least one finger down

2018-02-19 Thread Peter Hutterer
If a single-touch touchpad drops below the pressure threshold in the same
frame where a fake finger is added, we begin a fake touch here. The subsequent
loop ends this fake touch because real_fingers_down is 0.

This causes the tapping code to have a mismatch of how many fingers are down
because it never sees the touch begin event for that finger.

https://bugs.freedesktop.org/show_bug.cgi?id=105160
---
 src/evdev-mt-touchpad-tap.c |  1 +
 src/evdev-mt-touchpad.c | 16 +---
 test/test-touchpad-tap.c| 43 +++
 3 files changed, 53 insertions(+), 7 deletions(-)

diff --git a/src/evdev-mt-touchpad-tap.c b/src/evdev-mt-touchpad-tap.c
index eaf3a573..fadc9535 100644
--- a/src/evdev-mt-touchpad-tap.c
+++ b/src/evdev-mt-touchpad-tap.c
@@ -1027,6 +1027,7 @@ tp_tap_handle_state(struct tp_dispatch *tp, uint64_t time)
 
} else if (t->state == TOUCH_END) {
if (t->was_down) {
+   assert(tp->tap.nfingers_down >= 1);
tp->tap.nfingers_down--;
tp_tap_handle_event(tp, t, TAP_EVENT_RELEASE, 
time);
}
diff --git a/src/evdev-mt-touchpad.c b/src/evdev-mt-touchpad.c
index 02ad9dd8..b3ed6d56 100644
--- a/src/evdev-mt-touchpad.c
+++ b/src/evdev-mt-touchpad.c
@@ -1102,14 +1102,16 @@ tp_unhover_pressure(struct tp_dispatch *tp, uint64_t 
time)
 * _all_ fingers have enough pressure, even if some of the slotted
 * ones don't. Anything else gets insane quickly.
 */
-   tp_for_each_touch(tp, t) {
-   if (t->state == TOUCH_HOVERING) {
-   /* avoid jumps when landing a finger */
-   tp_motion_history_reset(t);
-   tp_begin_touch(tp, t, time);
+   if (real_fingers_down > 0) {
+   tp_for_each_touch(tp, t) {
+   if (t->state == TOUCH_HOVERING) {
+   /* avoid jumps when landing a finger */
+   tp_motion_history_reset(t);
+   tp_begin_touch(tp, t, time);
 
-   if (tp->nfingers_down >= nfake_touches)
-   break;
+   if (tp->nfingers_down >= nfake_touches)
+   break;
+   }
}
}
 
diff --git a/test/test-touchpad-tap.c b/test/test-touchpad-tap.c
index 06caeb20..0616ae22 100644
--- a/test/test-touchpad-tap.c
+++ b/test/test-touchpad-tap.c
@@ -1591,6 +1591,48 @@ START_TEST(touchpad_3fg_tap_quickrelease)
 }
 END_TEST
 
+START_TEST(touchpad_3fg_tap_hover_btntool)
+{
+   struct litest_device *dev = litest_current_device();
+   struct libinput *li = dev->libinput;
+
+   if (libevdev_get_abs_maximum(dev->evdev,
+ABS_MT_SLOT) >= 2)
+   return;
+
+   litest_enable_tap(dev->libinput_device);
+   litest_enable_edge_scroll(dev);
+
+   litest_drain_events(li);
+
+   litest_touch_down(dev, 0, 50, 50);
+   litest_touch_down(dev, 1, 70, 50);
+   libinput_dispatch(li);
+
+   litest_touch_move_to(dev, 0, 50, 50, 50, 70, 10, 0);
+   litest_touch_move_to(dev, 1, 70, 50, 50, 70, 10, 0);
+   litest_drain_events(li);
+
+   /* drop below the pressure threshold in the same frame as starting a */
+   litest_event(dev, EV_ABS, ABS_MT_PRESSURE, 3);
+   litest_event(dev, EV_ABS, ABS_PRESSURE, 3);
+   litest_event(dev, EV_KEY, BTN_TOUCH, 0);
+   litest_event(dev, EV_KEY, BTN_TOOL_DOUBLETAP, 0);
+   litest_event(dev, EV_KEY, BTN_TOOL_TRIPLETAP, 1);
+   litest_event(dev, EV_SYN, SYN_REPORT, 0);
+   libinput_dispatch(li);
+
+   litest_push_event_frame(dev);
+   litest_event(dev, EV_KEY, BTN_TOOL_DOUBLETAP, 1);
+   litest_event(dev, EV_KEY, BTN_TOOL_TRIPLETAP, 0);
+   litest_pop_event_frame(dev);
+   litest_assert_empty_queue(li);
+
+   litest_touch_up(dev, 0);
+   litest_touch_up(dev, 1);
+}
+END_TEST
+
 START_TEST(touchpad_3fg_tap_btntool)
 {
struct litest_device *dev = litest_current_device();
@@ -3273,6 +3315,7 @@ litest_setup_tests_touchpad_tap(void)
litest_add_ranged("tap-3fg:3fg", touchpad_3fg_tap, LITEST_TOUCHPAD, 
LITEST_SINGLE_TOUCH, &tap_map_range);
litest_add("tap-3fg:3fg", touchpad_3fg_tap_tap_again, LITEST_TOUCHPAD, 
LITEST_SINGLE_TOUCH);
litest_add("tap-3fg:3fg", touchpad_3fg_tap_quickrelease, 
LITEST_TOUCHPAD, LITEST_SINGLE_TOUCH);
+   litest_add("tap-3fg:3fg", touchpad_3fg_tap_hover_btntool, 
LITEST_TOUCHPAD, LITEST_SINGLE_TOUCH);
litest_add_for_device("tap-3fg:3fg", 
touchpad_3fg_tap_btntool_pointerjump, LITEST_SYNAPTICS_TOPBUTTONPAD);
litest_add("tap-4fg:4fg", touchpad_4fg_tap, LITEST_TOUCHPAD, 
LITEST_SINGLE_TOUCH|LITEST_SEMI_MT);
litest_add("tap-4fg:4fg", touchpad_4fg_tap_q

Re: [PATCH 0/2 libinput] [RFC] Add touchpad wobbliness detection

2018-02-19 Thread Konstantin Kharlamov
FWIW, given peoples complained about hysteresis algo latency, I'm also 
poking around with alternative hysteresis algos. One possible idea that 
came to my mind is to use the detection code posted here to figure the 
maximum wobbliness length (along each axis separately), then simply 
ignore movements of that length. No idea how's that gonna work, will 
check on holidays.


On 19.02.2018 10:59, Peter Hutterer wrote:

On Sun, Feb 18, 2018 at 01:09:22PM +0300, Konstantin Kharlamov wrote:

For the purposes it seems to work fine — it's marked RFC because I see a
small oddness, and I think it's better to ask someone more
acknowledgable in libinput codebase.


thanks, much appreciated. I was hoping I get to this today but didn't, I'll
try for it tomorrow. meanwhile:



For some reason every time I run

libinput debug-events --verbose | grep bled

I see a message about hysteresis being enabled, which then never appears
until I stop the command, and re-run it again. It looks like every time
the command ran, touchpad being reinitialized, making the function
tp_init_hysteresis() to ran again.
  
it's expected, yes. debug-events instantiates a new libinput context (you

can't get to the one in the compositor) and your code, from a quick glance,
only runs until enabled. so every time you start the tool, you start from
zero.

Cheers,
Peter


If this is an intentional behavior, then I have no other question, and
the patchset should be fine. Though it would be nice if someone with a
"non-wobbly" touchpad could test that it does not enable hysteresis for
them (it all should be good, but testing never hurts :)


P.S.: I don't have commit rights.

Konstantin Kharlamov (2):
   touchpad: remove the code for disabling hysteresis
   touchpad: add wobbling detection

  src/evdev-mt-touchpad.c | 42 --
  src/evdev-mt-touchpad.h |  1 +
  2 files changed, 29 insertions(+), 14 deletions(-)

--
2.15.1

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


[RFC weston 2/2] compositor-x11: Use event loop abstraction API

2018-02-19 Thread Quentin Glidic
From: Quentin Glidic 

Signed-off-by: Quentin Glidic 
---
 libweston/compositor-x11.c | 64 +-
 1 file changed, 29 insertions(+), 35 deletions(-)

diff --git a/libweston/compositor-x11.c b/libweston/compositor-x11.c
index 14faeda03..7675b7275 100644
--- a/libweston/compositor-x11.c
+++ b/libweston/compositor-x11.c
@@ -81,7 +81,7 @@ struct x11_backend {
xcb_screen_t*screen;
xcb_cursor_t null_cursor;
struct wl_array  keys;
-   struct wl_event_source  *xcb_source;
+   void*xcb_source;
struct xkb_keymap   *xkb_keymap;
unsigned int has_xkb;
uint8_t  xkb_event_base;
@@ -122,7 +122,7 @@ struct x11_output {
xcb_window_twindow;
struct weston_mode  mode;
struct weston_mode  native;
-   struct wl_event_source *finish_frame_timer;
+   void   *finish_frame_timer;
 
xcb_gc_tgc;
xcb_shm_seg_t   segment;
@@ -411,7 +411,9 @@ x11_output_repaint_gl(struct weston_output *output_base,
pixman_region32_subtract(&ec->primary_plane.damage,
 &ec->primary_plane.damage, damage);
 
-   wl_event_source_timer_update(output->finish_frame_timer, 10);
+   weston_compositor_event_source_update_timeout(ec,
+ 
output->finish_frame_timer,
+ 10);
return 0;
 }
 
@@ -498,11 +500,13 @@ x11_output_repaint_shm(struct weston_output *output_base,
free(err);
}
 
-   wl_event_source_timer_update(output->finish_frame_timer, 10);
+   weston_compositor_event_source_update_timeout(ec,
+ 
output->finish_frame_timer,
+ 10);
return 0;
 }
 
-static int
+static enum weston_event_source_status
 finish_frame_handler(void *data)
 {
struct x11_output *output = data;
@@ -511,7 +515,7 @@ finish_frame_handler(void *data)
weston_compositor_read_presentation_clock(output->base.compositor, &ts);
weston_output_finish_frame(&output->base, &ts, 0);
 
-   return 1;
+   return WESTON_EVENT_SOURCE_CONTINUE;
 }
 
 static void
@@ -874,7 +878,8 @@ x11_output_disable(struct weston_output *base)
if (!output->base.enabled)
return 0;
 
-   wl_event_source_remove(output->finish_frame_timer);
+   weston_compositor_event_source_remove(base->compositor,
+ output->finish_frame_timer);
 
if (backend->use_pixman) {
pixman_renderer_output_destroy(&output->base);
@@ -1044,7 +1049,11 @@ x11_output_enable(struct weston_output *base)
 
loop = wl_display_get_event_loop(b->compositor->wl_display);
output->finish_frame_timer =
-   wl_event_loop_add_timer(loop, finish_frame_handler, output);
+   weston_compositor_event_source_add_timeout(base->compositor,
+  
WESTON_EVENT_SOURCE_PRIORITY_TIMEOUT,
+  0,
+  finish_frame_handler,
+  output);
 
weston_log("x11 output %dx%d, window id %d\n",
   output->base.current_mode->width,
@@ -1394,20 +1403,8 @@ x11_backend_deliver_enter_event(struct x11_backend *b,
b->prev_y = y;
 }
 
-static int
-x11_backend_next_event(struct x11_backend *b,
-  xcb_generic_event_t **event, uint32_t mask)
-{
-   if (mask & WL_EVENT_READABLE)
-   *event = xcb_poll_for_event(b->conn);
-   else
-   *event = xcb_poll_for_queued_event(b->conn);
-
-   return *event != NULL;
-}
-
-static int
-x11_backend_handle_event(int fd, uint32_t mask, void *data)
+static enum weston_event_source_status
+x11_backend_handle_event(int fd, enum weston_event_source_fd_events mask, void 
*data)
 {
struct x11_backend *b = data;
struct x11_output *output;
@@ -1424,12 +1421,10 @@ x11_backend_handle_event(int fd, uint32_t mask, void 
*data)
uint32_t *k;
uint32_t i, set;
uint8_t response_type;
-   int count;
struct timespec time;
 
prev = NULL;
-   count = 0;
-   while (x11_backend_next_event(b, &event, mask)) {
+   while ((event = xcb_poll_for_event(b->conn)) != NULL) {
response_type = event->response_type & ~0x80;
 
switch (prev ? prev->response_type & ~0x80 : 0x80) {
@@ -1637,7 +1632,6 @@ x11_backend_handle_event(int fd, uint32_t mask, void 
*data)
}
 #endif
 
-   count++;
if (prev != event)
  

[RFC weston 0/2] Event loop abstraction API

2018-02-19 Thread Quentin Glidic
From: Quentin Glidic 

We discussed on IRC about races between the several event sources that
exist in libweston, libwayland and compositor code. Adding a priority
system in the event loop is a first step to fix these potential races
and help cope with bad clients.
A second issue is that compositor writers are usually used to some
specific event loop library (GLib, Qt, libev or any other) with
differences in APIs and some frameworks are tied to one.

To make things easier to compositor writers, here is a draft for an
event loop API abstraction that should allow to pick any library to work
with libweston.
(Still lacking the signal handling part.)

Sending as RFC to check if the API is fine by Weston contributors before
migrating all the codebase to it.

Cheers,

Quentin Glidic (2):
  libweston: Add event loop abstraction API
  compositor-x11: Use event loop abstraction API

 compositor/main.c  | 182 +++--
 libweston/compositor-x11.c |  64 
 libweston/compositor.c |  86 +
 libweston/compositor.h |  67 +
 4 files changed, 358 insertions(+), 41 deletions(-)

-- 
2.15.1

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


[RFC weston 1/2] libweston: Add event loop abstraction API

2018-02-19 Thread Quentin Glidic
From: Quentin Glidic 

This will allow compositors to pick any event loop implementation they
want, and integrating the libweston components with it.
Specifically, idle and timeout sources can now have proper priorities to
avoid being ghosted by client event processing.

Signed-off-by: Quentin Glidic 
---
 compositor/main.c  | 182 +++--
 libweston/compositor.c |  86 +++
 libweston/compositor.h |  67 ++
 3 files changed, 329 insertions(+), 6 deletions(-)

diff --git a/compositor/main.c b/compositor/main.c
index 18810f288..c0a5ba506 100644
--- a/compositor/main.c
+++ b/compositor/main.c
@@ -76,6 +76,180 @@ struct wet_compositor {
bool drm_use_current_mode;
 };
 
+static struct wet_compositor *
+to_wet_compositor(struct weston_compositor *compositor)
+{
+   return weston_compositor_get_user_data(compositor);
+}
+
+struct wet_event_source {
+   struct wl_event_loop *loop;
+   struct wl_event_source *source;
+   weston_event_source_callback cb;
+   weston_event_source_fd_callback fd_cb;
+   void *user_data;
+};
+
+static void
+wet_event_source_idle_cb(void *data)
+{
+   struct wet_event_source *wsource = data;
+   enum weston_event_source_status ret;
+
+   ret = wsource->cb(wsource->user_data);
+   if (ret == WESTON_EVENT_SOURCE_REMOVE)
+   return;
+
+   wsource->source = wl_event_loop_add_idle(wsource->loop, 
wet_event_source_idle_cb, wsource);
+   if (wsource->source == NULL)
+   free(wsource);
+}
+
+static void *
+wet_event_source_add_idle(struct weston_compositor *compositor,
+ enum weston_event_source_priority priority,
+ weston_event_source_callback cb, void *user_data)
+{
+   struct wet_event_source *wsource = malloc(sizeof(struct 
wet_event_source));
+   if (wsource == NULL)
+   return NULL;
+
+   wsource->loop = wl_display_get_event_loop(compositor->wl_display);
+   wsource->cb = cb;
+   wsource->user_data = user_data;
+
+   wsource->source = wl_event_loop_add_idle(wsource->loop, 
wet_event_source_idle_cb, wsource);
+   if (wsource->source == NULL) {
+   free(wsource);
+   return NULL;
+   }
+
+   return wsource;
+}
+
+static int
+wet_event_source_timeout_cb(void *data)
+{
+   struct wet_event_source *wsource = data;
+   enum weston_event_source_status ret;
+
+   ret = wsource->cb(wsource->user_data);
+   if (ret == WESTON_EVENT_SOURCE_CONTINUE)
+   return 0;
+
+   wl_event_source_remove(wsource->source);
+   free(wsource);
+   return 0;
+}
+
+static void *
+wet_event_source_add_timeout(struct weston_compositor *compositor,
+enum weston_event_source_priority priority,
+uint32_t milliseconds,
+weston_event_source_callback cb, void *user_data)
+{
+   struct wet_event_source *wsource = malloc(sizeof(struct 
wet_event_source));
+   if (wsource == NULL)
+   return NULL;
+
+   wsource->loop = wl_display_get_event_loop(compositor->wl_display);
+   wsource->cb = cb;
+   wsource->user_data = user_data;
+
+   wsource->source = wl_event_loop_add_timer(wsource->loop, 
wet_event_source_timeout_cb, wsource);
+   if (wsource->source == NULL) {
+   free(wsource);
+   return NULL;
+   }
+
+   if (milliseconds > 0)
+   wl_event_source_timer_update(wsource->source, milliseconds);
+
+   return wsource;
+}
+
+static void
+wet_event_source_update_timeout(struct weston_compositor *compositor,
+   void *source, uint32_t milliseconds)
+{
+   struct wet_event_source *wsource = source;
+
+   wl_event_source_timer_update(wsource->source, milliseconds);
+}
+
+static int
+wet_event_source_fd_cb(int fd, uint32_t mask, void *data)
+{
+   struct wet_event_source *wsource = data;
+   enum weston_event_source_status ret;
+
+   ret = wsource->fd_cb(fd, mask, wsource->user_data);
+   if (ret == WESTON_EVENT_SOURCE_CONTINUE)
+   return 0;
+
+   wl_event_source_remove(wsource->source);
+   free(wsource);
+   return 0;
+}
+
+static void *
+wet_event_source_add_fd(struct weston_compositor *compositor,
+   enum weston_event_source_priority priority,
+   int fd, enum weston_event_source_fd_events events,
+   weston_event_source_fd_callback cb, void *user_data)
+{
+   struct wet_event_source *wsource = malloc(sizeof(struct 
wet_event_source));
+   if (wsource == NULL)
+   return NULL;
+
+   wsource->loop = wl_display_get_event_loop(compositor->wl_display);
+   wsource->fd_cb = cb;
+   wsource->user_data = user_data;
+
+   wsource->source = wl_event_loop_add_fd(wsource->loop, fd, events, 
we

[PATCH] xwm: Update input region on resize

2018-02-19 Thread Scott Moreau
Commit 332d1892 introduced a bug because the window was
shaped only when the frame was created, leaving the input
region unchanged regardless if the window was resized.
This patch updates the input region shape on resize,
fixing the problem.
---
 xwayland/window-manager.c | 46 +++---
 1 file changed, 27 insertions(+), 19 deletions(-)

diff --git a/xwayland/window-manager.c b/xwayland/window-manager.c
index c307e19..5588166 100644
--- a/xwayland/window-manager.c
+++ b/xwayland/window-manager.c
@@ -659,6 +659,30 @@ weston_wm_window_get_input_rect(struct weston_wm_window 
*window,
 }
 
 static void
+weston_wm_window_shape(struct weston_wm_window *window)
+{
+   struct weston_wm *wm = window->wm;
+   xcb_rectangle_t rect;
+   int x, y, width, height;
+
+   weston_wm_window_get_input_rect(window, &x, &y, &width, &height);
+
+   rect.x = x;
+   rect.y = y;
+   rect.width = width;
+   rect.height = height;
+
+   /* The window frame was created with position and size which include
+* an offset for margins and shadow. Set the input region to ignore
+* shadow. */
+   xcb_shape_rectangles(wm->conn,
+XCB_SHAPE_SO_SET,
+XCB_SHAPE_SK_INPUT,
+0, window->frame_id,
+0, 0, 1, &rect);
+}
+
+static void
 weston_wm_window_send_configure_notify(struct weston_wm_window *window)
 {
xcb_configure_notify_event_t configure_notify;
@@ -789,6 +813,8 @@ weston_wm_handle_configure_notify(struct weston_wm *wm, 
xcb_generic_event_t *eve
xwayland_api->set_xwayland(window->shsurf,
   window->x, window->y);
}
+
+   weston_wm_window_shape(window);
 }
 
 static void
@@ -983,7 +1009,6 @@ weston_wm_window_create_frame(struct weston_wm_window 
*window)
 {
struct weston_wm *wm = window->wm;
uint32_t values[3];
-   xcb_rectangle_t rect;
int x, y, width, height;
int buttons = FRAME_BUTTON_CLOSE;
 
@@ -1040,24 +1065,7 @@ weston_wm_window_create_frame(struct weston_wm_window 
*window)
 &wm->format_rgba,
 width, height);
 
-   weston_wm_window_get_input_rect(window, &x, &y, &width, &height);
-   rect.x = x;
-   rect.y = y;
-   rect.width = width;
-   rect.height = height;
-
-   /* The window frame was created with position and size which include
-* an offset for margins and shadow. Set the input region to ignore
-* shadow. */
-   xcb_shape_rectangles(wm->conn,
-XCB_SHAPE_SO_SET,
-XCB_SHAPE_SK_INPUT,
-0,
-window->frame_id,
-0,
-0,
-1,
-&rect);
+   weston_wm_window_shape(window);
 
hash_table_insert(wm->window_hash, window->frame_id, window);
 }
-- 
2.7.4

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


[PATCH] compositor-drm: handle null cursor_plane

2018-02-19 Thread Greg V
Was crashing when I tried to take a screenshot.
---
On my slightly unconventional setup (FreeBSD amdgpu), after merging 
recent changes, pressing the screenshot hotkey was crashing weston.

Debugging revealed that cursor_plane was 0x0 here.
I don't know why exactly, but adding this check fixes it.

 libweston/compositor-drm.c | 6 --
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/libweston/compositor-drm.c b/libweston/compositor-drm.c
index ff090907..278bc02d 100644
--- a/libweston/compositor-drm.c
+++ b/libweston/compositor-drm.c
@@ -1830,8 +1830,10 @@ drm_output_apply_state_legacy(struct drm_output_state 
*state)
 */
if (output->base.disable_planes) {
output->cursor_view = NULL;
-   output->cursor_plane->base.x = INT32_MIN;
-   output->cursor_plane->base.y = INT32_MIN;
+   if (output->cursor_plane) {
+   output->cursor_plane->base.x = INT32_MIN;
+   output->cursor_plane->base.y = INT32_MIN;
+   }
}
 
if (state->dpms != WESTON_DPMS_ON) {
-- 
2.16.1

___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel


Re: [PATCH 0/2 libinput] [RFC] Add touchpad wobbliness detection

2018-02-19 Thread Peter Hutterer
On Sun, Feb 18, 2018 at 01:09:22PM +0300, Konstantin Kharlamov wrote:
> For the purposes it seems to work fine — it's marked RFC because I see a
> small oddness, and I think it's better to ask someone more
> acknowledgable in libinput codebase.

thanks, much appreciated. I was hoping I get to this today but didn't, I'll
try for it tomorrow. meanwhile:

> 
> For some reason every time I run 
> 
>   libinput debug-events --verbose | grep bled
> 
> I see a message about hysteresis being enabled, which then never appears
> until I stop the command, and re-run it again. It looks like every time
> the command ran, touchpad being reinitialized, making the function
> tp_init_hysteresis() to ran again.
 
it's expected, yes. debug-events instantiates a new libinput context (you
can't get to the one in the compositor) and your code, from a quick glance,
only runs until enabled. so every time you start the tool, you start from
zero.

Cheers,
   Peter

> If this is an intentional behavior, then I have no other question, and
> the patchset should be fine. Though it would be nice if someone with a
> "non-wobbly" touchpad could test that it does not enable hysteresis for
> them (it all should be good, but testing never hurts :)
>
> 
> P.S.: I don't have commit rights.
> 
> Konstantin Kharlamov (2):
>   touchpad: remove the code for disabling hysteresis
>   touchpad: add wobbling detection
> 
>  src/evdev-mt-touchpad.c | 42 --
>  src/evdev-mt-touchpad.h |  1 +
>  2 files changed, 29 insertions(+), 14 deletions(-)
> 
> -- 
> 2.15.1
> 
> ___
> wayland-devel mailing list
> wayland-devel@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/wayland-devel
> 
___
wayland-devel mailing list
wayland-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/wayland-devel