wayland: wl_display_dispatch_queue() can block forever.
authorVíctor Manuel Jáquez Leal <victorx.jaquez@intel.com>
Thu, 7 May 2015 10:33:34 +0000 (12:33 +0200)
committerVíctor Manuel Jáquez Leal <victorx.jaquez@intel.com>
Fri, 15 May 2015 15:10:37 +0000 (17:10 +0200)
wl_display_dispatch_queue() might prevent the pipeline from shutting
down. This can happen e.g. if the wayland compositor exits while the
pipeline is running.

This patch replaces it with these steps:

- With wl_display_prepare_read() all threads announce their intention
  to read.
- wl_display_read_events() is thread save. On threads reads, the other
  wait for it to finish.
- With wl_display_dispatch_queue_pending() each thread dispatches its
  own events.

wl_display_dispatch_queue_pending() was defined since wayland 1.0.2

Original-patch-by: Michael Olbrich <m.olbrich@pengutronix.de>
* stripped out the unlock() unlock_stop() logic
* stripped out the poll handling

Signed-off-by: Víctor Manuel Jáquez Leal <victorx.jaquez@intel.com>
https://bugzilla.gnome.org/show_bug.cgi?id=749078

https://bugzilla.gnome.org/show_bug.cgi?id=747492

configure.ac
gst-libs/gst/vaapi/gstvaapiwindow_wayland.c

index 22ff810..34fe92b 100644 (file)
@@ -38,7 +38,7 @@ m4_define([gst16_plugins_base_version], [1.5.0])
 m4_define([gst16_plugins_bad_version],  [1.5.0])
 
 # Wayland minimum version number
-m4_define([wayland_api_version], [1.0.0])
+m4_define([wayland_api_version], [1.0.2])
 
 # VA-API minimum version number
 m4_define([va_api_version],     [0.30.4])
index 9015c39..efb455c 100644 (file)
@@ -159,10 +159,23 @@ gst_vaapi_window_wayland_sync (GstVaapiWindow * window)
       GST_VAAPI_OBJECT_NATIVE_DISPLAY (window);
 
   while (g_atomic_int_get (&priv->num_frames_pending) > 0) {
-    if (wl_display_dispatch_queue (wl_display, priv->event_queue) < 0)
-      return FALSE;
+    while (wl_display_prepare_read_queue (wl_display, priv->event_queue) < 0) {
+      if (wl_display_dispatch_queue_pending (wl_display, priv->event_queue) < 0)
+        goto error;
+    }
+
+    if (wl_display_flush (wl_display) < 0)
+      goto error;
+    if (wl_display_read_events (wl_display) < 0)
+      goto error;
+    if (wl_display_dispatch_queue_pending (wl_display, priv->event_queue) < 0)
+      goto error;
   }
   return TRUE;
+
+error:
+  GST_ERROR ("Error on dispatching events: %s", g_strerror (errno));
+  return FALSE;
 }
 
 static void