diff options
Diffstat (limited to 'gst/sdp')
-rw-r--r-- | gst/sdp/Makefile.am | 4 | ||||
-rw-r--r-- | gst/sdp/gstsdpdemux.c | 156 | ||||
-rw-r--r-- | gst/sdp/gstsdpdemux.h | 9 |
3 files changed, 67 insertions, 102 deletions
diff --git a/gst/sdp/Makefile.am b/gst/sdp/Makefile.am index 77a1a9725..c1627c435 100644 --- a/gst/sdp/Makefile.am +++ b/gst/sdp/Makefile.am @@ -2,8 +2,8 @@ plugin_LTLIBRARIES = libgstsdpelem.la libgstsdpelem_la_SOURCES = gstsdpelem.c gstsdpdemux.h gstsdpdemux.c -libgstsdpelem_la_CFLAGS = $(GST_PLUGINS_BASE_CFLAGS) $(GST_CFLAGS) -libgstsdpelem_la_LIBADD = $(GST_PLUGINS_BASE_LIBS) $(GST_BASE_LIBS) \ +libgstsdpelem_la_CFLAGS = $(GST_PLUGINS_BASE_CFLAGS) $(GST_CFLAGS) $(GIO_CFLAGS) +libgstsdpelem_la_LIBADD = $(GST_PLUGINS_BASE_LIBS) $(GST_BASE_LIBS) $(GIO_LIBS) \ -lgstinterfaces-@GST_MAJORMINOR@ \ -lgstrtp-@GST_MAJORMINOR@ -lgstsdp-@GST_MAJORMINOR@ \ $(GST_LIBS) $(WIN32_LIBS) diff --git a/gst/sdp/gstsdpdemux.c b/gst/sdp/gstsdpdemux.c index 9b65b18bb..30e98fd09 100644 --- a/gst/sdp/gstsdpdemux.c +++ b/gst/sdp/gstsdpdemux.c @@ -20,7 +20,7 @@ * SECTION:element-sdpdemux * * sdpdemux currently understands SDP as the input format of the session description. - * For each stream listed in the SDP a new rtp_stream%d pad will be created + * For each stream listed in the SDP a new stream_%u pad will be created * with caps derived from the SDP media description. This is a caps of mime type * "application/x-rtp" that can be connected to any available RTP depayloader * element. @@ -51,39 +51,14 @@ * with newer GLib versions (>= 2.31.0) */ #define GLIB_DISABLE_DEPRECATION_WARNINGS -#ifdef HAVE_UNISTD_H -#include <unistd.h> -#endif - -/* include GLIB for G_OS_WIN32 */ -#include <glib.h> - -#ifdef G_OS_WIN32 -#ifdef _MSC_VER -#include <Winsock2.h> -#endif -/* ws2_32.dll has getaddrinfo and freeaddrinfo on Windows XP and later. - * * minwg32 headers check WINVER before allowing the use of these */ -#ifndef WINVER -#define WINVER 0x0501 -#endif -#include <ws2tcpip.h> -#else -#include <sys/socket.h> -#include <netdb.h> -#include <netinet/in.h> -#endif - -#include <stdlib.h> -#include <string.h> -#include <locale.h> -#include <stdio.h> -#include <stdarg.h> +#include "gstsdpdemux.h" #include <gst/rtp/gstrtppayloads.h> #include <gst/sdp/gstsdpmessage.h> -#include "gstsdpdemux.h" +#include <stdio.h> +#include <stdlib.h> +#include <string.h> GST_DEBUG_CATEGORY_STATIC (sdpdemux_debug); #define GST_CAT_DEFAULT (sdpdemux_debug) @@ -93,7 +68,7 @@ static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink", GST_PAD_ALWAYS, GST_STATIC_CAPS ("application/sdp")); -static GstStaticPadTemplate rtptemplate = GST_STATIC_PAD_TEMPLATE ("stream%d", +static GstStaticPadTemplate rtptemplate = GST_STATIC_PAD_TEMPLATE ("stream_%u", GST_PAD_SRC, GST_PAD_SOMETIMES, GST_STATIC_CAPS ("application/x-rtp")); @@ -136,34 +111,15 @@ static void gst_sdp_demux_handle_message (GstBin * bin, GstMessage * message); static void gst_sdp_demux_stream_push_event (GstSDPDemux * demux, GstSDPStream * stream, GstEvent * event); -static gboolean gst_sdp_demux_sink_event (GstPad * pad, GstEvent * event); -static GstFlowReturn gst_sdp_demux_sink_chain (GstPad * pad, +static gboolean gst_sdp_demux_sink_event (GstPad * pad, GstObject * parent, + GstEvent * event); +static GstFlowReturn gst_sdp_demux_sink_chain (GstPad * pad, GstObject * parent, GstBuffer * buffer); /*static guint gst_sdp_demux_signals[LAST_SIGNAL] = { 0 }; */ -static void -_do_init (GType sdp_demux_type) -{ - GST_DEBUG_CATEGORY_INIT (sdpdemux_debug, "sdpdemux", 0, "SDP demux"); -} - -GST_BOILERPLATE_FULL (GstSDPDemux, gst_sdp_demux, GstBin, GST_TYPE_BIN, - _do_init); - -static void -gst_sdp_demux_base_init (gpointer g_class) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (g_class); - - gst_element_class_add_static_pad_template (element_class, &sinktemplate); - gst_element_class_add_static_pad_template (element_class, &rtptemplate); - - gst_element_class_set_details_simple (element_class, "SDP session setup", - "Codec/Demuxer/Network/RTP", - "Receive data over the network via SDP", - "Wim Taymans <wim.taymans@gmail.com>"); -} +#define gst_sdp_demux_parent_class parent_class +G_DEFINE_TYPE (GstSDPDemux, gst_sdp_demux, GST_TYPE_BIN); static void gst_sdp_demux_class_init (GstSDPDemuxClass * klass) @@ -204,13 +160,25 @@ gst_sdp_demux_class_init (GstSDPDemuxClass * klass) DEFAULT_REDIRECT, G_PARAM_READWRITE | G_PARAM_CONSTRUCT | G_PARAM_STATIC_STRINGS)); + gst_element_class_add_pad_template (gstelement_class, + gst_static_pad_template_get (&sinktemplate)); + gst_element_class_add_pad_template (gstelement_class, + gst_static_pad_template_get (&rtptemplate)); + + gst_element_class_set_details_simple (gstelement_class, "SDP session setup", + "Codec/Demuxer/Network/RTP", + "Receive data over the network via SDP", + "Wim Taymans <wim.taymans@gmail.com>"); + gstelement_class->change_state = gst_sdp_demux_change_state; gstbin_class->handle_message = gst_sdp_demux_handle_message; + + GST_DEBUG_CATEGORY_INIT (sdpdemux_debug, "sdpdemux", 0, "SDP demux"); } static void -gst_sdp_demux_init (GstSDPDemux * demux, GstSDPDemuxClass * g_class) +gst_sdp_demux_init (GstSDPDemux * demux) { demux->sinkpad = gst_pad_new_from_static_template (&sinktemplate, "sink"); gst_pad_set_event_function (demux->sinkpad, @@ -221,8 +189,7 @@ gst_sdp_demux_init (GstSDPDemux * demux, GstSDPDemuxClass * g_class) /* protects the streaming thread in interleaved mode or the polling * thread in UDP mode. */ - demux->stream_rec_lock = g_new (GStaticRecMutex, 1); - g_static_rec_mutex_init (demux->stream_rec_lock); + g_rec_mutex_init (&demux->stream_rec_lock); demux->adapter = gst_adapter_new (); } @@ -235,8 +202,7 @@ gst_sdp_demux_finalize (GObject * object) demux = GST_SDP_DEMUX (object); /* free locks */ - g_static_rec_mutex_free (demux->stream_rec_lock); - g_free (demux->stream_rec_lock); + g_rec_mutex_clear (&demux->stream_rec_lock); g_object_unref (demux->adapter); @@ -383,32 +349,31 @@ gst_sdp_demux_stream_free (GstSDPDemux * demux, GstSDPStream * stream) static gboolean is_multicast_address (const gchar * host_name) { - struct addrinfo hints; - struct addrinfo *ai; - struct addrinfo *res; + GInetAddress *addr; + GResolver *resolver = NULL; gboolean ret = FALSE; - memset (&hints, 0, sizeof (hints)); - hints.ai_socktype = SOCK_DGRAM; - - g_return_val_if_fail (host_name, FALSE); + addr = g_inet_address_new_from_string (host_name); + if (!addr) { + GList *results; - if (getaddrinfo (host_name, NULL, &hints, &res) < 0) - return FALSE; + resolver = g_resolver_get_default (); + results = g_resolver_lookup_by_name (resolver, host_name, NULL, NULL); + if (!results) + goto out; + addr = G_INET_ADDRESS (g_object_ref (results->data)); - for (ai = res; !ret && ai; ai = ai->ai_next) { - if (ai->ai_family == AF_INET) - ret = - IN_MULTICAST (ntohl (((struct sockaddr_in *) ai->ai_addr)-> - sin_addr.s_addr)); - else - ret = - IN6_IS_ADDR_MULTICAST (&((struct sockaddr_in6 *) ai-> - ai_addr)->sin6_addr); + g_resolver_free_addresses (results); } + g_assert (addr != NULL); - freeaddrinfo (res); + ret = g_inet_address_get_is_multicast (addr); +out: + if (resolver) + g_object_unref (resolver); + if (addr) + g_object_unref (addr); return ret; } @@ -767,7 +732,7 @@ new_session_pad (GstElement * session, GstPad * pad, GstSDPDemux * demux) GST_SDP_STREAM_LOCK (demux); /* find stream */ name = gst_object_get_name (GST_OBJECT_CAST (pad)); - if (sscanf (name, "recv_rtp_src_%d_%d_%d", &id, &ssrc, &pt) != 3) + if (sscanf (name, "recv_rtp_src_%u_%u_%u", &id, &ssrc, &pt) != 3) goto unknown_stream; GST_DEBUG_OBJECT (demux, "stream: %u, SSRC %d, PT %d", id, ssrc, pt); @@ -948,7 +913,7 @@ gst_sdp_demux_configure_manager (GstSDPDemux * demux, char *rtsp_sdp) g_signal_connect (demux->session, "no-more-pads", (GCallback) rtsp_session_no_more_pads, demux); } else { - if (!(demux->session = gst_element_factory_make ("gstrtpbin", NULL))) + if (!(demux->session = gst_element_factory_make ("rtpbin", NULL))) goto manager_failed; /* connect to signals if we did not already do so */ @@ -1029,7 +994,7 @@ gst_sdp_demux_stream_configure_udp (GstSDPDemux * demux, GstSDPStream * stream) /* get output pad of the UDP source. */ pad = gst_element_get_static_pad (stream->udpsrc[0], "src"); - name = g_strdup_printf ("recv_rtp_sink_%d", stream->id); + name = g_strdup_printf ("recv_rtp_sink_%u", stream->id); stream->channelpad[0] = gst_element_get_request_pad (demux->session, name); g_free (name); @@ -1058,7 +1023,7 @@ gst_sdp_demux_stream_configure_udp (GstSDPDemux * demux, GstSDPStream * stream) GST_DEBUG_OBJECT (demux, "connecting RTCP source to manager"); - name = g_strdup_printf ("recv_rtcp_sink_%d", stream->id); + name = g_strdup_printf ("recv_rtcp_sink_%u", stream->id); stream->channelpad[1] = gst_element_get_request_pad (demux->session, name); g_free (name); @@ -1084,7 +1049,8 @@ gst_sdp_demux_stream_configure_udp_sink (GstSDPDemux * demux, GstSDPStream * stream) { GstPad *pad, *sinkpad; - gint port, sockfd = -1; + gint port; + GSocket *socket; gchar *destination, *uri, *name; /* get destination and port */ @@ -1117,12 +1083,13 @@ gst_sdp_demux_stream_configure_udp_sink (GstSDPDemux * demux, /* configure socket, we give it the same UDP socket as the udpsrc for RTCP * because some servers check the port number of where it sends RTCP to identify * the RTCP packets it receives */ - g_object_get (G_OBJECT (stream->udpsrc[1]), "sock", &sockfd, NULL); - GST_DEBUG_OBJECT (demux, "UDP src has sock %d", sockfd); + g_object_get (G_OBJECT (stream->udpsrc[1]), "used_socket", &socket, NULL); + GST_DEBUG_OBJECT (demux, "UDP src has socket %p", socket); /* configure socket and make sure udpsink does not close it when shutting * down, it belongs to udpsrc after all. */ - g_object_set (G_OBJECT (stream->udpsink), "sockfd", sockfd, NULL); - g_object_set (G_OBJECT (stream->udpsink), "closefd", FALSE, NULL); + g_object_set (G_OBJECT (stream->udpsink), "socket", socket, NULL); + g_object_set (G_OBJECT (stream->udpsink), "close-socket", FALSE, NULL); + g_object_unref (socket); } /* we keep this playing always */ @@ -1132,7 +1099,7 @@ gst_sdp_demux_stream_configure_udp_sink (GstSDPDemux * demux, gst_bin_add (GST_BIN_CAST (demux), stream->udpsink); /* get session RTCP pad */ - name = g_strdup_printf ("send_rtcp_src_%d", stream->id); + name = g_strdup_printf ("send_rtcp_src_%u", stream->id); pad = gst_element_get_request_pad (demux->session, name); g_free (name); @@ -1483,12 +1450,12 @@ start_session_failure: } static gboolean -gst_sdp_demux_sink_event (GstPad * pad, GstEvent * event) +gst_sdp_demux_sink_event (GstPad * pad, GstObject * parent, GstEvent * event) { GstSDPDemux *demux; gboolean res = TRUE; - demux = GST_SDP_DEMUX (gst_pad_get_parent (pad)); + demux = GST_SDP_DEMUX (parent); switch (GST_EVENT_TYPE (event)) { case GST_EVENT_EOS: @@ -1500,24 +1467,21 @@ gst_sdp_demux_sink_event (GstPad * pad, GstEvent * event) gst_event_unref (event); break; } - gst_object_unref (demux); return res; } static GstFlowReturn -gst_sdp_demux_sink_chain (GstPad * pad, GstBuffer * buffer) +gst_sdp_demux_sink_chain (GstPad * pad, GstObject * parent, GstBuffer * buffer) { GstSDPDemux *demux; - demux = GST_SDP_DEMUX (gst_pad_get_parent (pad)); + demux = GST_SDP_DEMUX (parent); /* push the SDP message in an adapter, we start doing something with it when * we receive EOS */ gst_adapter_push (demux->adapter, buffer); - gst_object_unref (demux); - return GST_FLOW_OK; } diff --git a/gst/sdp/gstsdpdemux.h b/gst/sdp/gstsdpdemux.h index 94db8d62c..c04cd293a 100644 --- a/gst/sdp/gstsdpdemux.h +++ b/gst/sdp/gstsdpdemux.h @@ -22,6 +22,7 @@ #include <gst/gst.h> #include <gst/base/gstadapter.h> +#include <gio/gio.h> G_BEGIN_DECLS @@ -41,9 +42,9 @@ G_BEGIN_DECLS typedef struct _GstSDPDemux GstSDPDemux; typedef struct _GstSDPDemuxClass GstSDPDemuxClass; -#define GST_SDP_STREAM_GET_LOCK(sdp) (GST_SDP_DEMUX_CAST(sdp)->stream_rec_lock) -#define GST_SDP_STREAM_LOCK(sdp) (g_static_rec_mutex_lock (GST_SDP_STREAM_GET_LOCK(sdp))) -#define GST_SDP_STREAM_UNLOCK(sdp) (g_static_rec_mutex_unlock (GST_SDP_STREAM_GET_LOCK(sdp))) +#define GST_SDP_STREAM_GET_LOCK(sdp) (&GST_SDP_DEMUX_CAST(sdp)->stream_rec_lock) +#define GST_SDP_STREAM_LOCK(sdp) (g_rec_mutex_lock (GST_SDP_STREAM_GET_LOCK(sdp))) +#define GST_SDP_STREAM_UNLOCK(sdp) (g_rec_mutex_unlock (GST_SDP_STREAM_GET_LOCK(sdp))) typedef struct _GstSDPStream GstSDPStream; @@ -90,7 +91,7 @@ struct _GstSDPDemux { gboolean ignore_timeout; gint numstreams; - GStaticRecMutex *stream_rec_lock; + GRecMutex stream_rec_lock; GList *streams; /* properties */ |