Don't require appsink be drained in appsink_readable release-2.x.y

Thu, 08 Oct 2015 12:50:16 +0200

author
Jakub Adam <jakub.adam@ktknet.cz>
date
Thu, 08 Oct 2015 12:50:16 +0200
branch
release-2.x.y
changeset 37244
cbc4db14444c
parent 37243
902b1fd334bd
child 37245
fc04ac95763d
child 37247
d8de636e63df

Don't require appsink be drained in appsink_readable

When appsink_readable was entered, it kept invoking the read callback
as long as there were some unread data available. This may have led to
infinite loop when the application decided it wasn't convenient to read
the whole input buffer just now.

This change removes the while loop and if some data are left in the
buffer, appsink_readable returns TRUE in order to be scheduled again.
Control returns to the main loop and another events get a chance to
be processed.

libpurple/mediamanager.c file | annotate | diff | comparison | revisions
--- a/libpurple/mediamanager.c	Wed Oct 07 23:39:22 2015 -0700
+++ b/libpurple/mediamanager.c	Thu Oct 08 12:50:16 2015 +0200
@@ -948,6 +948,7 @@
 	gpointer cb_data;
 	guint *cb_token_ptr = &info->readable_cb_token;
 	guint cb_token = *cb_token_ptr;
+	gboolean run_again = FALSE;
 
 	g_mutex_lock (&manager->priv->appdata_mutex);
 	if (cb_token == 0 || cb_token != *cb_token_ptr) {
@@ -955,8 +956,8 @@
 		g_mutex_unlock (&manager->priv->appdata_mutex);
 		return FALSE;
 	}
-	/* We need to signal readable until there are no more samples */
-	while (info->callbacks.readable &&
+
+	if (info->callbacks.readable &&
 		(info->num_samples > 0 || info->current_sample != NULL)) {
 		readable_cb = info->callbacks.readable;
 		media = g_weak_ref_get (&info->media_ref);
@@ -978,9 +979,17 @@
 			return FALSE;
 		}
 	}
-	info->readable_cb_token = 0;
+
+	/* Do we still have samples? Schedule appsink_readable again. We break here
+	 * so that other events get a chance to be processed too. */
+	if (info->num_samples > 0 || info->current_sample != NULL) {
+		run_again = TRUE;
+	} else {
+		info->readable_cb_token = 0;
+	}
+
 	g_mutex_unlock (&manager->priv->appdata_mutex);
-	return FALSE;
+	return run_again;
 }
 
 static void

mercurial