} G_STMT_END
/*static guint gst_rtspsrc_signals[LAST_SIGNAL] = { 0 }; */
-
-static void
-_do_init (GType rtspsrc_type)
-{
- static const GInterfaceInfo urihandler_info = {
- gst_rtspsrc_uri_handler_init,
- NULL,
- NULL
- };
-
- GST_DEBUG_CATEGORY_INIT (rtspsrc_debug, "rtspsrc", 0, "RTSP src");
-
- g_type_add_interface_static (rtspsrc_type, GST_TYPE_URI_HANDLER,
- &urihandler_info);
-}
-
-GST_BOILERPLATE_FULL (GstRTSPSrc, gst_rtspsrc, GstBin, GST_TYPE_BIN, _do_init);
-
-static void
-gst_rtspsrc_base_init (gpointer g_class)
-{
- GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
-
- gst_element_class_add_pad_template (element_class,
- gst_static_pad_template_get (&rtptemplate));
-
- gst_element_class_set_details_simple (element_class, "RTSP packet receiver",
- "Source/Network",
- "Receive data over the network via RTSP (RFC 2326)",
- "Wim Taymans <wim@fluendo.com>, "
- "Thijs Vermeir <thijs.vermeir@barco.com>, "
- "Lutz Mueller <lutz@topfrose.de>");
-}
+#define gst_rtspsrc_parent_class parent_class
+G_DEFINE_TYPE_WITH_CODE (GstRTSPSrc, gst_rtspsrc, GST_TYPE_BIN,
+ G_IMPLEMENT_INTERFACE (GST_TYPE_URI_HANDLER, gst_rtspsrc_uri_handler_init));
static void
gst_rtspsrc_class_init (GstRTSPSrcClass * klass)
gstelement_class = (GstElementClass *) klass;
gstbin_class = (GstBinClass *) klass;
+ GST_DEBUG_CATEGORY_INIT (rtspsrc_debug, "rtspsrc", 0, "RTSP src");
+
gobject_class->set_property = gst_rtspsrc_set_property;
gobject_class->get_property = gst_rtspsrc_get_property;
gstelement_class->send_event = gst_rtspsrc_send_event;
gstelement_class->change_state = gst_rtspsrc_change_state;
+ gst_element_class_add_pad_template (gstelement_class,
+ gst_static_pad_template_get (&rtptemplate));
+
+ gst_element_class_set_details_simple (gstelement_class,
+ "RTSP packet receiver", "Source/Network",
+ "Receive data over the network via RTSP (RFC 2326)",
+ "Wim Taymans <wim@fluendo.com>, "
+ "Thijs Vermeir <thijs.vermeir@barco.com>, "
+ "Lutz Mueller <lutz@topfrose.de>");
+
gstbin_class->handle_message = gst_rtspsrc_handle_message;
gst_rtsp_ext_list_init ();
static void
-gst_rtspsrc_init (GstRTSPSrc * src, GstRTSPSrcClass * g_class)
+gst_rtspsrc_init (GstRTSPSrc * src)
{
#ifdef G_OS_WIN32
WSADATA wsa_data;
/* we keep these elements, we configure all in configure_transport when the
* server told us to really use the UDP ports. */
- stream->udpsrc[0] = gst_object_ref (udpsrc0);
- stream->udpsrc[1] = gst_object_ref (udpsrc1);
+ stream->udpsrc[0] = gst_object_ref_sink (udpsrc0);
+ stream->udpsrc[1] = gst_object_ref_sink (udpsrc1);
/* keep track of next available port number when we have a range
* configured */
if (src->next_port_num != 0)
src->next_port_num = tmp_rtcp + 1;
- /* they are ours now */
- gst_object_sink (udpsrc0);
- gst_object_sink (udpsrc1);
-
return TRUE;
/* ERRORS */
cmd = CMD_WAIT;
state = GST_STATE_PAUSED;
} else {
- event = gst_event_new_flush_stop ();
+ event = gst_event_new_flush_stop (TRUE);
GST_DEBUG_OBJECT (src, "stop flush");
cmd = CMD_LOOP;
state = GST_STATE_PLAYING;
* right values in the segment to perform the seek */
if (event) {
GST_DEBUG_OBJECT (src, "configuring seek");
- gst_segment_set_seek (&seeksegment, rate, format, flags,
+ gst_segment_do_seek (&seeksegment, rate, format, flags,
cur_type, cur, stop_type, stop, &update);
}
/* if we started flush, we stop now */
GST_DEBUG_OBJECT (src, "stopping flush");
gst_rtspsrc_flush (src, FALSE);
- } else if (src->running) {
- /* re-engage loop */
- gst_rtspsrc_loop_send_cmd (src, CMD_LOOP, FALSE);
-
- /* we are running the current segment and doing a non-flushing seek,
- * close the segment first based on the previous last_stop. */
- GST_DEBUG_OBJECT (src, "closing running segment %" G_GINT64_FORMAT
- " to %" G_GINT64_FORMAT, src->segment.accum, src->segment.last_stop);
-
- /* queue the segment for sending in the stream thread */
- if (src->close_segment)
- gst_event_unref (src->close_segment);
- src->close_segment = gst_event_new_new_segment (TRUE,
- src->segment.rate, src->segment.format,
- src->segment.accum, src->segment.last_stop, src->segment.accum);
-
- /* keep track of our last_stop */
- seeksegment.accum = src->segment.last_stop;
}
/* now we did the seek and can activate the new segment values */
if (src->segment.flags & GST_SEEK_FLAG_SEGMENT) {
gst_element_post_message (GST_ELEMENT_CAST (src),
gst_message_new_segment_start (GST_OBJECT_CAST (src),
- src->segment.format, src->segment.last_stop));
+ src->segment.format, src->segment.position));
}
/* now create the newsegment */
GST_DEBUG_OBJECT (src, "Creating newsegment from %" G_GINT64_FORMAT
- " to %" G_GINT64_FORMAT, src->segment.last_stop, stop);
+ " to %" G_GINT64_FORMAT, src->segment.position, stop);
/* store the newsegment event so it can be sent from the streaming thread. */
if (src->start_segment)
gst_event_unref (src->start_segment);
- src->start_segment =
- gst_event_new_new_segment (FALSE, src->segment.rate,
- src->segment.format, src->segment.last_stop, stop,
- src->segment.last_stop);
+ src->start_segment = gst_event_new_segment (&src->segment);
/* mark discont */
GST_DEBUG_OBJECT (src, "mark DISCONT, we did a seek to another position");
GstFlowReturn res = GST_FLOW_OK;
guint8 *data;
guint size;
+ gsize bsize;
GstRTSPResult ret;
GstRTSPMessage message = { 0 };
GstRTSPConnection *conn;
stream = (GstRTSPStream *) gst_pad_get_element_private (pad);
src = stream->parent;
- data = GST_BUFFER_DATA (buffer);
- size = GST_BUFFER_SIZE (buffer);
+ data = gst_buffer_map (buffer, &bsize, NULL, GST_MAP_READ);
+ size = bsize;
gst_rtsp_message_init_data (&message, stream->channel[1]);
gst_rtsp_message_steal_body (&message, &data, &size);
gst_rtsp_message_unset (&message);
+ gst_buffer_unmap (buffer, data, size);
gst_buffer_unref (buffer);
return res;
}
-static void
-pad_unblocked (GstPad * pad, gboolean blocked, GstRTSPSrc * src)
+static GstProbeReturn
+pad_blocked (GstPad * pad, GstProbeType type, gpointer type_data,
+ gpointer user_data)
{
- GST_DEBUG_OBJECT (src, "pad %s:%s unblocked", GST_DEBUG_PAD_NAME (pad));
-}
+ GstRTSPSrc *src = user_data;
-static void
-pad_blocked (GstPad * pad, gboolean blocked, GstRTSPSrc * src)
-{
GST_DEBUG_OBJECT (src, "pad %s:%s blocked, activating streams",
GST_DEBUG_PAD_NAME (pad));
gst_rtspsrc_activate_streams (src);
- return;
+ return GST_PROBE_OK;
was_ok:
{
GST_OBJECT_UNLOCK (src);
- return;
+ return GST_PROBE_OK;
}
}
goto no_element;
/* take ownership */
- gst_object_ref (stream->udpsrc[0]);
- gst_object_sink (stream->udpsrc[0]);
+ gst_object_ref_sink (stream->udpsrc[0]);
/* change state */
gst_element_set_state (stream->udpsrc[0], GST_STATE_PAUSED);
goto no_element;
/* take ownership */
- gst_object_ref (stream->udpsrc[1]);
- gst_object_sink (stream->udpsrc[1]);
+ gst_object_ref_sink (stream->udpsrc[1]);
gst_element_set_state (stream->udpsrc[1], GST_STATE_PAUSED);
}
/* configure pad block on the pad. As soon as there is dataflow on the
* UDP source, we know that UDP is not blocked by a firewall and we can
* configure all the streams to let the application autoplug decoders. */
- gst_pad_set_blocked_async (stream->blockedpad, TRUE,
- (GstPadBlockCallback) pad_blocked, src);
+ stream->blockid =
+ gst_pad_add_probe (stream->blockedpad, GST_PROBE_TYPE_BLOCK,
+ pad_blocked, src, NULL);
if (stream->channelpad[0]) {
GST_DEBUG_OBJECT (src, "connecting UDP source 0 to manager");
for (walk = src->streams; walk; walk = g_list_next (walk)) {
GstRTSPStream *stream = (GstRTSPStream *) walk->data;
- if (stream->blockedpad) {
+ if (stream->blockid) {
GST_DEBUG_OBJECT (src, "unblocking stream pad %p", stream);
- gst_pad_set_blocked_async (stream->blockedpad, FALSE,
- (GstPadBlockCallback) pad_unblocked, src);
- stream->blockedpad = NULL;
+ gst_pad_remove_probe (stream->blockedpad, stream->blockid);
+ stream->blockid = 0;
}
}
GST_DEBUG_OBJECT (src, "configuring stream caps");
- start = segment->last_stop;
+ start = segment->position;
stop = segment->duration;
play_speed = segment->rate;
play_scale = segment->applied_rate;
size -= 1;
buf = gst_buffer_new ();
- GST_BUFFER_DATA (buf) = data;
- GST_BUFFER_MALLOCDATA (buf) = data;
- GST_BUFFER_SIZE (buf) = size;
+ gst_buffer_take_memory (buf, -1,
+ gst_memory_new_wrapped (0, data, g_free, size, 0, size));
/* don't need message anymore */
gst_rtsp_message_unset (&message);
src->need_activate = FALSE;
}
- if (!src->manager) {
- /* set stream caps on buffer when we don't have a session manager to do it
- * for us */
- gst_buffer_set_caps (buf, stream->caps);
- }
-
if (src->base_time == -1) {
/* Take current running_time. This timestamp will be put on
* the first buffer of each stream because we are a live source and so we
if (src->segment.flags & GST_SEEK_FLAG_SEGMENT) {
gst_element_post_message (GST_ELEMENT_CAST (src),
gst_message_new_segment_done (GST_OBJECT_CAST (src),
- src->segment.format, src->segment.last_stop));
+ src->segment.format, src->segment.position));
} else {
gst_rtspsrc_push_event (src, gst_event_new_eos (), FALSE);
}
/* we need to start playback without clipping from the position reported by
* the server */
segment->start = seconds;
- segment->last_stop = seconds;
+ segment->position = seconds;
if (therange->max.type == GST_RTSP_TIME_NOW)
seconds = -1;
/* don't change duration with unknown value, we might have a valid value
* there that we want to keep. */
if (seconds != -1)
- gst_segment_set_duration (segment, GST_FORMAT_TIME, seconds);
+ segment->duration = seconds;
return TRUE;
}
if (src->range && src->range->min.type == GST_RTSP_TIME_NOW) {
g_strlcpy (val_str, "now", sizeof (val_str));
} else {
- if (segment->last_stop == 0) {
+ if (segment->position == 0) {
g_strlcpy (val_str, "0", sizeof (val_str));
} else {
g_ascii_dtostr (val_str, sizeof (val_str),
- ((gdouble) segment->last_stop) / GST_SECOND);
+ ((gdouble) segment->position) / GST_SECOND);
}
}
return g_strdup_printf ("npt=%s-", val_str);
/* NOTE the above also disables npt based eos detection */
/* and below forces position to 0,
* which is visible feedback we lost the plot */
- segment->start = segment->last_stop = src->last_pos;
+ segment->start = segment->position = src->last_pos;
}
gst_rtsp_message_unset (&request);
/*** GSTURIHANDLER INTERFACE *************************************************/
static GstURIType
-gst_rtspsrc_uri_get_type (void)
+gst_rtspsrc_uri_get_type (GType type)
{
return GST_URI_SRC;
}
static gchar **
-gst_rtspsrc_uri_get_protocols (void)
+gst_rtspsrc_uri_get_protocols (GType type)
{
static const gchar *protocols[] =
{ "rtsp", "rtspu", "rtspt", "rtsph", "rtsp-sdp", NULL };