imagefreeze: Protect the flushing-seek variable by the srcpad's stream lock
authorSebastian Dröge <sebastian.droege@collabora.co.uk>
Fri, 20 Aug 2010 08:24:33 +0000 (10:24 +0200)
committerSebastian Dröge <sebastian.droege@collabora.co.uk>
Sat, 4 Sep 2010 12:52:08 +0000 (14:52 +0200)
This fixes a subtle race condition, that caused bufferalloc to fail
with wrong-state due to a seek but caused it to be not retried as
it should.

gst/imagefreeze/gstimagefreeze.c
gst/imagefreeze/gstimagefreeze.h

index 2b21906d9a624aa37ea7d331ec07a3c59feb6c20..b8e99772c9477cb34a5c01e5f40e5d8c3683896e 100644 (file)
@@ -329,9 +329,16 @@ gst_image_freeze_sink_bufferalloc (GstPad * pad, guint64 offset, guint size,
   GST_OBJECT_UNLOCK (self);
 
   if (do_alloc) {
+    gboolean seeking = FALSE;
+
     do {
+      GST_PAD_STREAM_LOCK (self->srcpad);
       ret = gst_pad_alloc_buffer (self->srcpad, offset, size, caps, buf);
-    } while (ret == GST_FLOW_WRONG_STATE && g_atomic_int_get (&self->seeking));
+
+      seeking = ret == GST_FLOW_WRONG_STATE
+          && g_atomic_int_get (&self->seeking);
+      GST_PAD_STREAM_UNLOCK (self->srcpad);
+    } while (seeking);
 
     if (G_UNLIKELY (ret != GST_FLOW_OK))
       GST_ERROR_OBJECT (pad, "Allocating buffer failed: %s",
index b9bc53f39c549e7b3538af3b254a8f9ef9680f3c..fff8c2ea3e326104385c71253b1843acf62ecac2 100644 (file)
@@ -56,7 +56,8 @@ struct _GstImageFreeze
 
   guint64 offset;
 
-  /* TRUE if currently doing a flushing seek */
+  /* TRUE if currently doing a flushing seek, protected
+   * by srcpad's stream lock */
   gint seeking;
 };