mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-18 15:51:11 +00:00
gst/rtsp/: Add URI handler.
Original commit message from CVS: * gst/rtsp/gstrtspsrc.c: (gst_rtspsrc_get_type), (gst_rtspsrc_parse_rtpmap), (gst_rtspsrc_media_to_caps), (gst_rtspsrc_stream_setup_rtp), (gst_rtspsrc_send), (gst_rtspsrc_open), (gst_rtspsrc_uri_get_type), (gst_rtspsrc_uri_get_protocols), (gst_rtspsrc_uri_get_uri), (gst_rtspsrc_uri_set_uri), (gst_rtspsrc_uri_handler_init): * gst/rtsp/sdpmessage.c: (sdp_media_get_format): * gst/rtsp/sdpmessage.h: Add URI handler. Parse SDP and create caps.
This commit is contained in:
parent
6982196218
commit
eb20f045f8
4 changed files with 204 additions and 9 deletions
13
ChangeLog
13
ChangeLog
|
@ -1,3 +1,16 @@
|
||||||
|
2005-09-20 Wim Taymans <wim@fluendo.com>
|
||||||
|
|
||||||
|
* gst/rtsp/gstrtspsrc.c: (gst_rtspsrc_get_type),
|
||||||
|
(gst_rtspsrc_parse_rtpmap), (gst_rtspsrc_media_to_caps),
|
||||||
|
(gst_rtspsrc_stream_setup_rtp), (gst_rtspsrc_send),
|
||||||
|
(gst_rtspsrc_open), (gst_rtspsrc_uri_get_type),
|
||||||
|
(gst_rtspsrc_uri_get_protocols), (gst_rtspsrc_uri_get_uri),
|
||||||
|
(gst_rtspsrc_uri_set_uri), (gst_rtspsrc_uri_handler_init):
|
||||||
|
* gst/rtsp/sdpmessage.c: (sdp_media_get_format):
|
||||||
|
* gst/rtsp/sdpmessage.h:
|
||||||
|
Add URI handler.
|
||||||
|
Parse SDP and create caps.
|
||||||
|
|
||||||
2005-09-20 Stefan Kost <ensonic@users.sf.net>
|
2005-09-20 Stefan Kost <ensonic@users.sf.net>
|
||||||
|
|
||||||
* gst/alpha/gstalpha.c:
|
* gst/alpha/gstalpha.c:
|
||||||
|
|
|
@ -88,6 +88,9 @@ static void gst_rtspsrc_base_init (gpointer g_class);
|
||||||
static void gst_rtspsrc_class_init (GstRTSPSrc * klass);
|
static void gst_rtspsrc_class_init (GstRTSPSrc * klass);
|
||||||
static void gst_rtspsrc_init (GstRTSPSrc * rtspsrc);
|
static void gst_rtspsrc_init (GstRTSPSrc * rtspsrc);
|
||||||
|
|
||||||
|
static void gst_rtspsrc_uri_handler_init (gpointer g_iface,
|
||||||
|
gpointer iface_data);
|
||||||
|
|
||||||
static GstStateChangeReturn gst_rtspsrc_change_state (GstElement * element,
|
static GstStateChangeReturn gst_rtspsrc_change_state (GstElement * element,
|
||||||
GstStateChange transition);
|
GstStateChange transition);
|
||||||
|
|
||||||
|
@ -120,10 +123,18 @@ gst_rtspsrc_get_type (void)
|
||||||
(GInstanceInitFunc) gst_rtspsrc_init,
|
(GInstanceInitFunc) gst_rtspsrc_init,
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
|
static const GInterfaceInfo urihandler_info = {
|
||||||
|
gst_rtspsrc_uri_handler_init,
|
||||||
|
NULL,
|
||||||
|
NULL
|
||||||
|
};
|
||||||
|
|
||||||
rtspsrc_type =
|
rtspsrc_type =
|
||||||
g_type_register_static (GST_TYPE_ELEMENT, "GstRTSPSrc", &rtspsrc_info,
|
g_type_register_static (GST_TYPE_ELEMENT, "GstRTSPSrc", &rtspsrc_info,
|
||||||
0);
|
0);
|
||||||
|
|
||||||
|
g_type_add_interface_static (rtspsrc_type, GST_TYPE_URI_HANDLER,
|
||||||
|
&urihandler_info);
|
||||||
}
|
}
|
||||||
return rtspsrc_type;
|
return rtspsrc_type;
|
||||||
}
|
}
|
||||||
|
@ -289,11 +300,125 @@ done:
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
gst_rtspsrc_stream_setup_rtp (GstRTSPStream * stream, gint * rtpport,
|
gst_rtspsrc_parse_rtpmap (gchar * rtpmap, gint * payload, gchar ** name,
|
||||||
gint * rtcpport)
|
gint * rate, gchar ** params)
|
||||||
|
{
|
||||||
|
gchar *p, *t;
|
||||||
|
|
||||||
|
t = p = rtpmap;
|
||||||
|
|
||||||
|
p = strstr (p, " ");
|
||||||
|
if (p == NULL)
|
||||||
|
return FALSE;
|
||||||
|
*p = '\0';
|
||||||
|
p++;
|
||||||
|
|
||||||
|
*payload = atoi (t);
|
||||||
|
|
||||||
|
while (*p && g_ascii_isspace (*p))
|
||||||
|
p++;
|
||||||
|
|
||||||
|
if (*p == '\0')
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
t = p;
|
||||||
|
p = strstr (p, "/");
|
||||||
|
if (p == NULL)
|
||||||
|
return FALSE;
|
||||||
|
*p = '\0';
|
||||||
|
p++;
|
||||||
|
*name = t;
|
||||||
|
|
||||||
|
t = p;
|
||||||
|
p = strstr (p, "/");
|
||||||
|
if (p == NULL) {
|
||||||
|
*rate = atoi (t);
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
*p = '\0';
|
||||||
|
p++;
|
||||||
|
*rate = atoi (t);
|
||||||
|
|
||||||
|
t = p;
|
||||||
|
if (*p == '\0')
|
||||||
|
return TRUE;
|
||||||
|
*params = t;
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Mapping of caps to and from SDP fields:
|
||||||
|
*
|
||||||
|
* m=<media> <udp port> RTP/AVP <payload>
|
||||||
|
* a=rtpmap:<payload> <encoding_name>/<clock_rate>[/<encoding_params>]
|
||||||
|
* a=fmtp:<payload> <param>=<value>;...
|
||||||
|
*/
|
||||||
|
static GstCaps *
|
||||||
|
gst_rtspsrc_media_to_caps (SDPMedia * media)
|
||||||
|
{
|
||||||
|
GstCaps *caps;
|
||||||
|
gchar *payload;
|
||||||
|
gchar *rtpmap;
|
||||||
|
|
||||||
|
//gchar *fmtp;
|
||||||
|
gint pt;
|
||||||
|
gchar *name = NULL;
|
||||||
|
gint rate = -1;
|
||||||
|
gchar *params = NULL;
|
||||||
|
GstStructure *s;
|
||||||
|
|
||||||
|
payload = sdp_media_get_format (media, 0);
|
||||||
|
if (payload == NULL) {
|
||||||
|
g_warning ("payload type not given");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
pt = atoi (payload);
|
||||||
|
|
||||||
|
if (pt >= 96) {
|
||||||
|
gint payload = 0;
|
||||||
|
gboolean ret;
|
||||||
|
|
||||||
|
rtpmap = sdp_media_get_attribute_val (media, "rtpmap");
|
||||||
|
if (rtpmap == NULL) {
|
||||||
|
g_warning ("rtpmap type not given");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
ret = gst_rtspsrc_parse_rtpmap (rtpmap, &payload, &name, &rate, ¶ms);
|
||||||
|
if (!ret) {
|
||||||
|
g_warning ("error parsing rtpmap");
|
||||||
|
}
|
||||||
|
if (payload != pt) {
|
||||||
|
g_warning ("rtpmap of wrong payload type");
|
||||||
|
name = NULL;
|
||||||
|
rate = -1;
|
||||||
|
params = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
caps = gst_caps_new_simple ("application/x-rtp",
|
||||||
|
"media", G_TYPE_STRING, media->media, "payload", G_TYPE_INT, pt, NULL);
|
||||||
|
s = gst_caps_get_structure (caps, 0);
|
||||||
|
|
||||||
|
if (rate != -1)
|
||||||
|
gst_structure_set (s, "clock-rate", G_TYPE_INT, rate, NULL);
|
||||||
|
|
||||||
|
if (name != NULL)
|
||||||
|
gst_structure_set (s, "encoding-name", G_TYPE_STRING, name, NULL);
|
||||||
|
|
||||||
|
if (params != NULL)
|
||||||
|
gst_structure_set (s, "encoding-params", G_TYPE_STRING, params, NULL);
|
||||||
|
|
||||||
|
return caps;
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_rtspsrc_stream_setup_rtp (GstRTSPStream * stream, SDPMedia * media,
|
||||||
|
gint * rtpport, gint * rtcpport)
|
||||||
{
|
{
|
||||||
GstStateChangeReturn ret;
|
GstStateChangeReturn ret;
|
||||||
GstRTSPSrc *src;
|
GstRTSPSrc *src;
|
||||||
|
GstCaps *caps;
|
||||||
|
|
||||||
src = stream->parent;
|
src = stream->parent;
|
||||||
|
|
||||||
|
@ -319,6 +444,10 @@ gst_rtspsrc_stream_setup_rtp (GstRTSPStream * stream, gint * rtpport,
|
||||||
if (ret == GST_STATE_CHANGE_FAILURE)
|
if (ret == GST_STATE_CHANGE_FAILURE)
|
||||||
goto start_rtcp_failure;
|
goto start_rtcp_failure;
|
||||||
|
|
||||||
|
caps = gst_rtspsrc_media_to_caps (media);
|
||||||
|
|
||||||
|
g_object_set (G_OBJECT (stream->rtpsrc), "caps", caps, NULL);
|
||||||
|
|
||||||
g_object_get (G_OBJECT (stream->rtpsrc), "port", rtpport, NULL);
|
g_object_get (G_OBJECT (stream->rtpsrc), "port", rtpport, NULL);
|
||||||
g_object_get (G_OBJECT (stream->rtcpsrc), "port", rtcpport, NULL);
|
g_object_get (G_OBJECT (stream->rtcpsrc), "port", rtcpport, NULL);
|
||||||
|
|
||||||
|
@ -514,12 +643,11 @@ gst_rtspsrc_send (GstRTSPSrc * src, RTSPMessage * request,
|
||||||
*code = response->type_data.response.code;
|
*code = response->type_data.response.code;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (response->type_data.response.code != RTSP_STS_OK)
|
|
||||||
goto error_response;
|
|
||||||
|
|
||||||
if (src->debug) {
|
if (src->debug) {
|
||||||
rtsp_message_dump (response);
|
rtsp_message_dump (response);
|
||||||
}
|
}
|
||||||
|
if (response->type_data.response.code != RTSP_STS_OK)
|
||||||
|
goto error_response;
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
|
||||||
|
@ -537,9 +665,9 @@ receive_error:
|
||||||
}
|
}
|
||||||
error_response:
|
error_response:
|
||||||
{
|
{
|
||||||
rtsp_message_dump (request);
|
GST_ELEMENT_ERROR (src, RESOURCE, READ, ("Got error response: %d (%s).",
|
||||||
rtsp_message_dump (response);
|
response->type_data.response.code,
|
||||||
GST_ELEMENT_ERROR (src, RESOURCE, READ, ("Got error response."), (NULL));
|
response->type_data.response.reason), (NULL));
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -706,7 +834,7 @@ gst_rtspsrc_open (GstRTSPSrc * src)
|
||||||
gchar *trxparams;
|
gchar *trxparams;
|
||||||
|
|
||||||
/* allocate two udp ports */
|
/* allocate two udp ports */
|
||||||
if (!gst_rtspsrc_stream_setup_rtp (stream, &rtpport, &rtcpport))
|
if (!gst_rtspsrc_stream_setup_rtp (stream, media, &rtpport, &rtcpport))
|
||||||
goto setup_rtp_failed;
|
goto setup_rtp_failed;
|
||||||
|
|
||||||
trxparams = g_strdup_printf ("client_port=%d-%d", rtpport, rtcpport);
|
trxparams = g_strdup_printf ("client_port=%d-%d", rtpport, rtcpport);
|
||||||
|
@ -1022,3 +1150,48 @@ open_failed:
|
||||||
return GST_STATE_CHANGE_FAILURE;
|
return GST_STATE_CHANGE_FAILURE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*** GSTURIHANDLER INTERFACE *************************************************/
|
||||||
|
|
||||||
|
static guint
|
||||||
|
gst_rtspsrc_uri_get_type (void)
|
||||||
|
{
|
||||||
|
return GST_URI_SRC;
|
||||||
|
}
|
||||||
|
static gchar **
|
||||||
|
gst_rtspsrc_uri_get_protocols (void)
|
||||||
|
{
|
||||||
|
static gchar *protocols[] = { "rtsp", NULL };
|
||||||
|
|
||||||
|
return protocols;
|
||||||
|
}
|
||||||
|
|
||||||
|
static const gchar *
|
||||||
|
gst_rtspsrc_uri_get_uri (GstURIHandler * handler)
|
||||||
|
{
|
||||||
|
GstRTSPSrc *src = GST_RTSPSRC (handler);
|
||||||
|
|
||||||
|
return g_strdup (src->location);
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_rtspsrc_uri_set_uri (GstURIHandler * handler, const gchar * uri)
|
||||||
|
{
|
||||||
|
GstRTSPSrc *src = GST_RTSPSRC (handler);
|
||||||
|
|
||||||
|
g_free (src->location);
|
||||||
|
src->location = g_strdup (uri);
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gst_rtspsrc_uri_handler_init (gpointer g_iface, gpointer iface_data)
|
||||||
|
{
|
||||||
|
GstURIHandlerInterface *iface = (GstURIHandlerInterface *) g_iface;
|
||||||
|
|
||||||
|
iface->get_type = gst_rtspsrc_uri_get_type;
|
||||||
|
iface->get_protocols = gst_rtspsrc_uri_get_protocols;
|
||||||
|
iface->get_uri = gst_rtspsrc_uri_get_uri;
|
||||||
|
iface->set_uri = gst_rtspsrc_uri_set_uri;
|
||||||
|
}
|
||||||
|
|
|
@ -399,6 +399,14 @@ sdp_media_get_attribute_val (SDPMedia * media, gchar * key)
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
gchar *
|
||||||
|
sdp_media_get_format (SDPMedia * media, gint i)
|
||||||
|
{
|
||||||
|
if (i >= media->fmts->len)
|
||||||
|
return NULL;
|
||||||
|
return g_array_index (media->fmts, gchar *, i);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
read_string (gchar * dest, gint size, gchar ** src)
|
read_string (gchar * dest, gint size, gchar ** src)
|
||||||
{
|
{
|
||||||
|
|
|
@ -158,6 +158,7 @@ RTSPResult sdp_media_clean (SDPMedia *media);
|
||||||
RTSPResult sdp_media_free (SDPMedia *media);
|
RTSPResult sdp_media_free (SDPMedia *media);
|
||||||
|
|
||||||
gchar* sdp_media_get_attribute_val (SDPMedia *media, gchar *key);
|
gchar* sdp_media_get_attribute_val (SDPMedia *media, gchar *key);
|
||||||
|
gchar* sdp_media_get_format (SDPMedia *media, gint i);
|
||||||
|
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
|
Loading…
Reference in a new issue