[farsight2/master] Make sure the same udpsock is not created twice in mcast

Olivier Crête olivier.crete at collabora.co.uk
Sun Dec 28 14:11:44 PST 2008


---
 transmitters/multicast/fs-multicast-transmitter.c |   55 ++++++++++++++++-----
 1 files changed, 42 insertions(+), 13 deletions(-)

diff --git a/transmitters/multicast/fs-multicast-transmitter.c b/transmitters/multicast/fs-multicast-transmitter.c
index 5ddb7c9..62bc305 100644
--- a/transmitters/multicast/fs-multicast-transmitter.c
+++ b/transmitters/multicast/fs-multicast-transmitter.c
@@ -746,8 +746,8 @@ _create_sinksource (gchar *elementname, GstBin *bin,
   return NULL;
 }
 
-UdpSock *
-fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
+static UdpSock *
+fs_multicast_transmitter_get_udpsock_locked (FsMulticastTransmitter *trans,
     guint component_id,
     const gchar *local_ip,
     const gchar *multicast_ip,
@@ -758,16 +758,6 @@ fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
   UdpSock *udpsock;
   GList *udpsock_e;
 
-  /* First lets check if we already have one */
-  if (component_id > trans->components)
-  {
-    g_set_error (error, FS_ERROR, FS_ERROR_INVALID_ARGUMENTS,
-      "Invalid component %d > %d", component_id, trans->components);
-    return NULL;
-  }
-
-  g_mutex_lock (trans->priv->mutex);
-
   for (udpsock_e = g_list_first (trans->priv->udpsocks[component_id]);
        udpsock_e;
        udpsock_e = g_list_next (udpsock_e))
@@ -788,7 +778,6 @@ fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
           g_set_error (error, FS_ERROR, FS_ERROR_INVALID_ARGUMENTS,
               "Error setting the multicast TTL: %s",
               g_strerror (errno));
-          g_mutex_unlock (trans->priv->mutex);
           return NULL;
         }
         udpsock->current_ttl = ttl;
@@ -798,8 +787,37 @@ fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
       return udpsock;
     }
   }
+  return NULL;
+}
+
+UdpSock *
+fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
+    guint component_id,
+    const gchar *local_ip,
+    const gchar *multicast_ip,
+    guint16 port,
+    guint8 ttl,
+    GError **error)
+{
+  UdpSock *udpsock;
+  UdpSock *tmpudpsock;
+
+  /* First lets check if we already have one */
+  if (component_id > trans->components)
+  {
+    g_set_error (error, FS_ERROR, FS_ERROR_INVALID_ARGUMENTS,
+      "Invalid component %d > %d", component_id, trans->components);
+    return NULL;
+  }
+
+  g_mutex_lock (trans->priv->mutex);
+  udpsock = fs_multicast_transmitter_get_udpsock_locked (trans, component_id,
+      local_ip, multicast_ip, port, ttl, error);
   g_mutex_unlock (trans->priv->mutex);
 
+  if (udpsock)
+    return udpsock;
+
   udpsock = g_slice_new0 (UdpSock);
 
   udpsock->local_ip = g_strdup (local_ip);
@@ -840,6 +858,17 @@ fs_multicast_transmitter_get_udpsock (FsMulticastTransmitter *trans,
       NULL);
 
   g_mutex_lock (trans->priv->mutex);
+  /* Check if someone else has added the same thing at the same time */
+  tmpudpsock = fs_multicast_transmitter_get_udpsock_locked (trans, component_id,
+      local_ip, multicast_ip, port, ttl, error);
+
+  if (tmpudpsock)
+  {
+    g_mutex_unlock (trans->priv->mutex);
+    fs_multicast_transmitter_put_udpsock (trans, udpsock, ttl);
+    return tmpudpsock;
+  }
+
   trans->priv->udpsocks[component_id] =
     g_list_prepend (trans->priv->udpsocks[component_id], udpsock);
   g_mutex_unlock (trans->priv->mutex);
-- 
1.5.6.5




More information about the farsight-commits mailing list