mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-02-14 18:25:22 +00:00
docs/design/part-seeking.txt: Some small additions.
Original commit message from CVS: * docs/design/part-seeking.txt: Some small additions. * gst/base/gstbasesink.c: (gst_base_sink_handle_object), (gst_base_sink_get_times), (gst_base_sink_do_sync), (gst_base_sink_activate_push), (gst_base_sink_activate_pull): * gst/base/gstbasesink.h: discont values are gint64, handle the math correctly. * gst/base/gstbasesrc.c: (gst_base_src_loop): Make the basesrc report error if the source pad is not linked. * gst/gstqueue.c: (gst_queue_link_src), (gst_queue_chain), (gst_queue_loop), (gst_queue_handle_src_query), (gst_queue_src_activate_push): Make queue collect data even if the srcpad is not linked. Start pushing out data as soon as it is linked. * gst/gstutils.c: (gst_element_unlink), (gst_flow_get_name): * gst/gstutils.h: Added gst_flow_get_name() to ease error reporting.
This commit is contained in:
parent
e261956ca6
commit
030ff93e82
12 changed files with 190 additions and 35 deletions
24
ChangeLog
24
ChangeLog
|
@ -1,3 +1,27 @@
|
||||||
|
2005-07-21 Wim Taymans <wim@fluendo.com>
|
||||||
|
|
||||||
|
* docs/design/part-seeking.txt:
|
||||||
|
Some small additions.
|
||||||
|
|
||||||
|
* gst/base/gstbasesink.c: (gst_base_sink_handle_object),
|
||||||
|
(gst_base_sink_get_times), (gst_base_sink_do_sync),
|
||||||
|
(gst_base_sink_activate_push), (gst_base_sink_activate_pull):
|
||||||
|
* gst/base/gstbasesink.h:
|
||||||
|
discont values are gint64, handle the math correctly.
|
||||||
|
|
||||||
|
* gst/base/gstbasesrc.c: (gst_base_src_loop):
|
||||||
|
Make the basesrc report error if the source pad is not linked.
|
||||||
|
|
||||||
|
* gst/gstqueue.c: (gst_queue_link_src), (gst_queue_chain),
|
||||||
|
(gst_queue_loop), (gst_queue_handle_src_query),
|
||||||
|
(gst_queue_src_activate_push):
|
||||||
|
Make queue collect data even if the srcpad is not linked.
|
||||||
|
Start pushing out data as soon as it is linked.
|
||||||
|
|
||||||
|
* gst/gstutils.c: (gst_element_unlink), (gst_flow_get_name):
|
||||||
|
* gst/gstutils.h:
|
||||||
|
Added gst_flow_get_name() to ease error reporting.
|
||||||
|
|
||||||
2005-07-20 Wim Taymans <wim@fluendo.com>
|
2005-07-20 Wim Taymans <wim@fluendo.com>
|
||||||
|
|
||||||
* gst/gstmessage.c: (gst_message_new_segment_start),
|
* gst/gstmessage.c: (gst_message_new_segment_start),
|
||||||
|
|
|
@ -2,7 +2,7 @@ Seeking
|
||||||
-------
|
-------
|
||||||
|
|
||||||
Seeking in GStreamer means configuring the pipeline for playback of the
|
Seeking in GStreamer means configuring the pipeline for playback of the
|
||||||
media between a certain start and stop time.
|
media between a certain start and stop time, called a segment.
|
||||||
|
|
||||||
Different kinds of seeking exist:
|
Different kinds of seeking exist:
|
||||||
|
|
||||||
|
@ -30,6 +30,10 @@ earliest element in the pipeline, typically a demuxer. After receiving
|
||||||
the message, the application can reconnect the pipeline or issue other
|
the message, the application can reconnect the pipeline or issue other
|
||||||
seek events in the pipeline.
|
seek events in the pipeline.
|
||||||
|
|
||||||
|
The seek can also change the playback speed of the configured segment.
|
||||||
|
A speed of 1.0 is normal speed, 2.0 is double speed. Negative values
|
||||||
|
mean backward playback.
|
||||||
|
|
||||||
|
|
||||||
Generating seeking events
|
Generating seeking events
|
||||||
-------------------------
|
-------------------------
|
||||||
|
|
|
@ -472,8 +472,7 @@ gst_base_sink_handle_object (GstBaseSink * basesink, GstPad * pad,
|
||||||
/* the discont event is needed to bring the buffer timestamps to the
|
/* the discont event is needed to bring the buffer timestamps to the
|
||||||
* stream time */
|
* stream time */
|
||||||
if (!gst_event_discont_get_value (event, GST_FORMAT_TIME,
|
if (!gst_event_discont_get_value (event, GST_FORMAT_TIME,
|
||||||
(gint64 *) & basesink->discont_start,
|
&basesink->discont_start, &basesink->discont_stop)) {
|
||||||
(gint64 *) & basesink->discont_stop)) {
|
|
||||||
basesink->discont_start = 0;
|
basesink->discont_start = 0;
|
||||||
basesink->discont_stop = 0;
|
basesink->discont_stop = 0;
|
||||||
}
|
}
|
||||||
|
@ -730,15 +729,26 @@ gst_base_sink_get_times (GstBaseSink * basesink, GstBuffer * buffer,
|
||||||
|
|
||||||
timestamp = GST_BUFFER_TIMESTAMP (buffer);
|
timestamp = GST_BUFFER_TIMESTAMP (buffer);
|
||||||
if (GST_CLOCK_TIME_IS_VALID (timestamp)) {
|
if (GST_CLOCK_TIME_IS_VALID (timestamp)) {
|
||||||
|
GstClockTimeDiff diff;
|
||||||
|
|
||||||
/* bring timestamp to stream time using last
|
/* bring timestamp to stream time using last
|
||||||
* discont offset. */
|
* discont offset. */
|
||||||
timestamp -= basesink->discont_start;
|
if ((diff = timestamp - basesink->discont_start) < 0)
|
||||||
|
goto too_late;
|
||||||
|
|
||||||
/* get duration to calculate end time */
|
/* get duration to calculate end time */
|
||||||
duration = GST_BUFFER_DURATION (buffer);
|
duration = GST_BUFFER_DURATION (buffer);
|
||||||
if (GST_CLOCK_TIME_IS_VALID (duration)) {
|
if (GST_CLOCK_TIME_IS_VALID (duration)) {
|
||||||
*end = timestamp + duration;
|
*end = diff + duration;
|
||||||
}
|
}
|
||||||
*start = timestamp;
|
*start = diff;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
|
||||||
|
too_late:
|
||||||
|
{
|
||||||
|
*start = GST_CLOCK_TIME_NONE;
|
||||||
|
*end = GST_CLOCK_TIME_NONE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -67,8 +67,8 @@ struct _GstBaseSink {
|
||||||
GstClockTime end_time;
|
GstClockTime end_time;
|
||||||
|
|
||||||
gboolean have_discont;
|
gboolean have_discont;
|
||||||
GstClockTime discont_start;
|
GstClockTimeDiff discont_start;
|
||||||
GstClockTime discont_stop;
|
GstClockTimeDiff discont_stop;
|
||||||
|
|
||||||
gboolean eos;
|
gboolean eos;
|
||||||
gboolean need_preroll;
|
gboolean need_preroll;
|
||||||
|
|
|
@ -702,11 +702,11 @@ pause:
|
||||||
{
|
{
|
||||||
GST_DEBUG_OBJECT (src, "pausing task");
|
GST_DEBUG_OBJECT (src, "pausing task");
|
||||||
gst_pad_pause_task (pad);
|
gst_pad_pause_task (pad);
|
||||||
if (GST_FLOW_IS_FATAL (ret)) {
|
if (GST_FLOW_IS_FATAL (ret) || ret == GST_FLOW_NOT_LINKED) {
|
||||||
/* for fatal errors we post an error message */
|
/* for fatal errors we post an error message */
|
||||||
GST_ELEMENT_ERROR (src, STREAM, STOPPED,
|
GST_ELEMENT_ERROR (src, STREAM, STOPPED,
|
||||||
("streaming stopped, reason %d", ret),
|
("streaming stopped, reason %s", gst_flow_get_name (ret)),
|
||||||
("streaming stopped, reason %d", ret));
|
("streaming stopped, reason %s", gst_flow_get_name (ret)));
|
||||||
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
|
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -29,6 +29,7 @@
|
||||||
#include "gstevent.h"
|
#include "gstevent.h"
|
||||||
#include "gstinfo.h"
|
#include "gstinfo.h"
|
||||||
#include "gsterror.h"
|
#include "gsterror.h"
|
||||||
|
#include "gstutils.h"
|
||||||
|
|
||||||
static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
|
static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
|
||||||
GST_PAD_SINK,
|
GST_PAD_SINK,
|
||||||
|
@ -406,10 +407,28 @@ static GstPadLinkReturn
|
||||||
gst_queue_link_src (GstPad * pad, GstPad * peer)
|
gst_queue_link_src (GstPad * pad, GstPad * peer)
|
||||||
{
|
{
|
||||||
GstPadLinkReturn result = GST_PAD_LINK_OK;
|
GstPadLinkReturn result = GST_PAD_LINK_OK;
|
||||||
|
GstQueue *queue;
|
||||||
|
|
||||||
/* FIXME, see if we need to push or get pulled */
|
queue = GST_QUEUE (gst_pad_get_parent (pad));
|
||||||
if (GST_PAD_LINKFUNC (peer))
|
|
||||||
|
GST_DEBUG ("queue linking source pad");
|
||||||
|
|
||||||
|
if (GST_PAD_LINKFUNC (peer)) {
|
||||||
result = GST_PAD_LINKFUNC (peer) (peer, pad);
|
result = GST_PAD_LINKFUNC (peer) (peer, pad);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (GST_PAD_LINK_SUCCESSFUL (result)) {
|
||||||
|
GST_QUEUE_MUTEX_LOCK (queue);
|
||||||
|
if (queue->srcresult == GST_FLOW_OK) {
|
||||||
|
gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
||||||
|
GST_DEBUG ("starting task as pad is linked");
|
||||||
|
} else {
|
||||||
|
GST_DEBUG ("not starting task reason %s",
|
||||||
|
gst_flow_get_name (queue->srcresult));
|
||||||
|
}
|
||||||
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
}
|
||||||
|
gst_object_unref (queue);
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -673,9 +692,10 @@ out_unref:
|
||||||
out_flushing:
|
out_flushing:
|
||||||
{
|
{
|
||||||
GstFlowReturn ret = queue->srcresult;
|
GstFlowReturn ret = queue->srcresult;
|
||||||
|
const gchar *flowname = gst_flow_get_name (ret);
|
||||||
|
|
||||||
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
||||||
"exit because task paused, reason: %d", ret);
|
"exit because task paused, reason: %s", flowname);
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
|
||||||
gst_buffer_unref (buffer);
|
gst_buffer_unref (buffer);
|
||||||
|
@ -746,13 +766,18 @@ restart:
|
||||||
/* can opt to check for srcresult here but the push should
|
/* can opt to check for srcresult here but the push should
|
||||||
* return an error value that is more accurate */
|
* return an error value that is more accurate */
|
||||||
if (result != GST_FLOW_OK) {
|
if (result != GST_FLOW_OK) {
|
||||||
|
const gchar *flowname;
|
||||||
|
|
||||||
|
flowname = gst_flow_get_name (result);
|
||||||
|
|
||||||
queue->srcresult = result;
|
queue->srcresult = result;
|
||||||
if (GST_FLOW_IS_FATAL (result)) {
|
if (GST_FLOW_IS_FATAL (result)) {
|
||||||
GST_ELEMENT_ERROR (queue, STREAM, STOPPED,
|
GST_ELEMENT_ERROR (queue, STREAM, STOPPED,
|
||||||
("streaming stopped, reason %d", result),
|
("streaming stopped, reason %s", flowname),
|
||||||
("streaming stopped, reason %d", result));
|
("streaming stopped, reason %s", flowname));
|
||||||
gst_pad_push_event (queue->srcpad, gst_event_new (GST_EVENT_EOS));
|
gst_pad_push_event (queue->srcpad, gst_event_new (GST_EVENT_EOS));
|
||||||
}
|
}
|
||||||
|
GST_DEBUG ("pausing queue, reason %s", flowname);
|
||||||
gst_pad_pause_task (queue->srcpad);
|
gst_pad_pause_task (queue->srcpad);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -760,6 +785,7 @@ restart:
|
||||||
/* all incomming data is now unexpected */
|
/* all incomming data is now unexpected */
|
||||||
queue->srcresult = GST_FLOW_UNEXPECTED;
|
queue->srcresult = GST_FLOW_UNEXPECTED;
|
||||||
/* and we don't need to process anymore */
|
/* and we don't need to process anymore */
|
||||||
|
GST_DEBUG ("pausing queue, we're EOS now");
|
||||||
gst_pad_pause_task (queue->srcpad);
|
gst_pad_pause_task (queue->srcpad);
|
||||||
restart = FALSE;
|
restart = FALSE;
|
||||||
}
|
}
|
||||||
|
@ -780,8 +806,10 @@ restart:
|
||||||
|
|
||||||
out_flushing:
|
out_flushing:
|
||||||
{
|
{
|
||||||
|
const gchar *flowname = gst_flow_get_name (queue->srcresult);
|
||||||
|
|
||||||
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
||||||
"exit because task paused, reason: %d", queue->srcresult);
|
"exit because task paused, reason: %s", flowname);
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
|
@ -890,7 +918,13 @@ gst_queue_src_activate_push (GstPad * pad, gboolean active)
|
||||||
if (active) {
|
if (active) {
|
||||||
GST_QUEUE_MUTEX_LOCK (queue);
|
GST_QUEUE_MUTEX_LOCK (queue);
|
||||||
queue->srcresult = GST_FLOW_OK;
|
queue->srcresult = GST_FLOW_OK;
|
||||||
|
/* we do not start the task yet if the pad is not connected */
|
||||||
|
if (gst_pad_is_linked (pad))
|
||||||
result = gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
result = gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
||||||
|
else {
|
||||||
|
GST_DEBUG ("not starting task as pad is not linked");
|
||||||
|
result = TRUE;
|
||||||
|
}
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
} else {
|
} else {
|
||||||
/* step 1, unblock chain and loop functions */
|
/* step 1, unblock chain and loop functions */
|
||||||
|
|
|
@ -1671,6 +1671,41 @@ gst_pad_get_parent_element (GstPad * pad)
|
||||||
return GST_ELEMENT_CAST (p);
|
return GST_ELEMENT_CAST (p);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* gst_flow_get_name:
|
||||||
|
* @state: a #GstFlowReturn to get the name of.
|
||||||
|
*
|
||||||
|
* Gets a string representing the given flow return.
|
||||||
|
*
|
||||||
|
* Returns: a string with the name of the flow return.
|
||||||
|
*/
|
||||||
|
G_CONST_RETURN gchar *
|
||||||
|
gst_flow_get_name (GstFlowReturn ret)
|
||||||
|
{
|
||||||
|
switch (ret) {
|
||||||
|
case GST_FLOW_RESEND:
|
||||||
|
return "need to resend buffer";
|
||||||
|
case GST_FLOW_OK:
|
||||||
|
return "OK";
|
||||||
|
/* expected failures */
|
||||||
|
case GST_FLOW_NOT_LINKED:
|
||||||
|
return "pad not linked";
|
||||||
|
case GST_FLOW_WRONG_STATE:
|
||||||
|
return "pad in wrong state";
|
||||||
|
/* error cases */
|
||||||
|
case GST_FLOW_UNEXPECTED:
|
||||||
|
return "unexpected data on pad";
|
||||||
|
case GST_FLOW_NOT_NEGOTIATED:
|
||||||
|
return "pad not negotiated";
|
||||||
|
case GST_FLOW_ERROR:
|
||||||
|
return "fatal error occured";
|
||||||
|
case GST_FLOW_NOT_SUPPORTED:
|
||||||
|
return "unsupported function called";
|
||||||
|
default:
|
||||||
|
return "unknown error";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* gst_object_default_error:
|
* gst_object_default_error:
|
||||||
* @object: a #GObject that signalled the error.
|
* @object: a #GObject that signalled the error.
|
||||||
|
|
|
@ -280,6 +280,10 @@ gboolean gst_pad_proxy_setcaps (GstPad * pad, GstCaps * caps);
|
||||||
|
|
||||||
GstElement* gst_pad_get_parent_element (GstPad *pad);
|
GstElement* gst_pad_get_parent_element (GstPad *pad);
|
||||||
|
|
||||||
|
/* flow */
|
||||||
|
G_CONST_RETURN gchar* gst_flow_get_name (GstFlowReturn ret);
|
||||||
|
|
||||||
|
|
||||||
/* util query functions */
|
/* util query functions */
|
||||||
gboolean gst_pad_query_position (GstPad *pad, GstFormat *format,
|
gboolean gst_pad_query_position (GstPad *pad, GstFormat *format,
|
||||||
gint64 *cur, gint64 *end);
|
gint64 *cur, gint64 *end);
|
||||||
|
|
|
@ -472,8 +472,7 @@ gst_base_sink_handle_object (GstBaseSink * basesink, GstPad * pad,
|
||||||
/* the discont event is needed to bring the buffer timestamps to the
|
/* the discont event is needed to bring the buffer timestamps to the
|
||||||
* stream time */
|
* stream time */
|
||||||
if (!gst_event_discont_get_value (event, GST_FORMAT_TIME,
|
if (!gst_event_discont_get_value (event, GST_FORMAT_TIME,
|
||||||
(gint64 *) & basesink->discont_start,
|
&basesink->discont_start, &basesink->discont_stop)) {
|
||||||
(gint64 *) & basesink->discont_stop)) {
|
|
||||||
basesink->discont_start = 0;
|
basesink->discont_start = 0;
|
||||||
basesink->discont_stop = 0;
|
basesink->discont_stop = 0;
|
||||||
}
|
}
|
||||||
|
@ -730,15 +729,26 @@ gst_base_sink_get_times (GstBaseSink * basesink, GstBuffer * buffer,
|
||||||
|
|
||||||
timestamp = GST_BUFFER_TIMESTAMP (buffer);
|
timestamp = GST_BUFFER_TIMESTAMP (buffer);
|
||||||
if (GST_CLOCK_TIME_IS_VALID (timestamp)) {
|
if (GST_CLOCK_TIME_IS_VALID (timestamp)) {
|
||||||
|
GstClockTimeDiff diff;
|
||||||
|
|
||||||
/* bring timestamp to stream time using last
|
/* bring timestamp to stream time using last
|
||||||
* discont offset. */
|
* discont offset. */
|
||||||
timestamp -= basesink->discont_start;
|
if ((diff = timestamp - basesink->discont_start) < 0)
|
||||||
|
goto too_late;
|
||||||
|
|
||||||
/* get duration to calculate end time */
|
/* get duration to calculate end time */
|
||||||
duration = GST_BUFFER_DURATION (buffer);
|
duration = GST_BUFFER_DURATION (buffer);
|
||||||
if (GST_CLOCK_TIME_IS_VALID (duration)) {
|
if (GST_CLOCK_TIME_IS_VALID (duration)) {
|
||||||
*end = timestamp + duration;
|
*end = diff + duration;
|
||||||
}
|
}
|
||||||
*start = timestamp;
|
*start = diff;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
|
||||||
|
too_late:
|
||||||
|
{
|
||||||
|
*start = GST_CLOCK_TIME_NONE;
|
||||||
|
*end = GST_CLOCK_TIME_NONE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -67,8 +67,8 @@ struct _GstBaseSink {
|
||||||
GstClockTime end_time;
|
GstClockTime end_time;
|
||||||
|
|
||||||
gboolean have_discont;
|
gboolean have_discont;
|
||||||
GstClockTime discont_start;
|
GstClockTimeDiff discont_start;
|
||||||
GstClockTime discont_stop;
|
GstClockTimeDiff discont_stop;
|
||||||
|
|
||||||
gboolean eos;
|
gboolean eos;
|
||||||
gboolean need_preroll;
|
gboolean need_preroll;
|
||||||
|
|
|
@ -702,11 +702,11 @@ pause:
|
||||||
{
|
{
|
||||||
GST_DEBUG_OBJECT (src, "pausing task");
|
GST_DEBUG_OBJECT (src, "pausing task");
|
||||||
gst_pad_pause_task (pad);
|
gst_pad_pause_task (pad);
|
||||||
if (GST_FLOW_IS_FATAL (ret)) {
|
if (GST_FLOW_IS_FATAL (ret) || ret == GST_FLOW_NOT_LINKED) {
|
||||||
/* for fatal errors we post an error message */
|
/* for fatal errors we post an error message */
|
||||||
GST_ELEMENT_ERROR (src, STREAM, STOPPED,
|
GST_ELEMENT_ERROR (src, STREAM, STOPPED,
|
||||||
("streaming stopped, reason %d", ret),
|
("streaming stopped, reason %s", gst_flow_get_name (ret)),
|
||||||
("streaming stopped, reason %d", ret));
|
("streaming stopped, reason %s", gst_flow_get_name (ret)));
|
||||||
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
|
gst_pad_push_event (pad, gst_event_new (GST_EVENT_EOS));
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -29,6 +29,7 @@
|
||||||
#include "gstevent.h"
|
#include "gstevent.h"
|
||||||
#include "gstinfo.h"
|
#include "gstinfo.h"
|
||||||
#include "gsterror.h"
|
#include "gsterror.h"
|
||||||
|
#include "gstutils.h"
|
||||||
|
|
||||||
static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
|
static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
|
||||||
GST_PAD_SINK,
|
GST_PAD_SINK,
|
||||||
|
@ -406,10 +407,28 @@ static GstPadLinkReturn
|
||||||
gst_queue_link_src (GstPad * pad, GstPad * peer)
|
gst_queue_link_src (GstPad * pad, GstPad * peer)
|
||||||
{
|
{
|
||||||
GstPadLinkReturn result = GST_PAD_LINK_OK;
|
GstPadLinkReturn result = GST_PAD_LINK_OK;
|
||||||
|
GstQueue *queue;
|
||||||
|
|
||||||
/* FIXME, see if we need to push or get pulled */
|
queue = GST_QUEUE (gst_pad_get_parent (pad));
|
||||||
if (GST_PAD_LINKFUNC (peer))
|
|
||||||
|
GST_DEBUG ("queue linking source pad");
|
||||||
|
|
||||||
|
if (GST_PAD_LINKFUNC (peer)) {
|
||||||
result = GST_PAD_LINKFUNC (peer) (peer, pad);
|
result = GST_PAD_LINKFUNC (peer) (peer, pad);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (GST_PAD_LINK_SUCCESSFUL (result)) {
|
||||||
|
GST_QUEUE_MUTEX_LOCK (queue);
|
||||||
|
if (queue->srcresult == GST_FLOW_OK) {
|
||||||
|
gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
||||||
|
GST_DEBUG ("starting task as pad is linked");
|
||||||
|
} else {
|
||||||
|
GST_DEBUG ("not starting task reason %s",
|
||||||
|
gst_flow_get_name (queue->srcresult));
|
||||||
|
}
|
||||||
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
}
|
||||||
|
gst_object_unref (queue);
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -673,9 +692,10 @@ out_unref:
|
||||||
out_flushing:
|
out_flushing:
|
||||||
{
|
{
|
||||||
GstFlowReturn ret = queue->srcresult;
|
GstFlowReturn ret = queue->srcresult;
|
||||||
|
const gchar *flowname = gst_flow_get_name (ret);
|
||||||
|
|
||||||
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
||||||
"exit because task paused, reason: %d", ret);
|
"exit because task paused, reason: %s", flowname);
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
|
||||||
gst_buffer_unref (buffer);
|
gst_buffer_unref (buffer);
|
||||||
|
@ -746,13 +766,18 @@ restart:
|
||||||
/* can opt to check for srcresult here but the push should
|
/* can opt to check for srcresult here but the push should
|
||||||
* return an error value that is more accurate */
|
* return an error value that is more accurate */
|
||||||
if (result != GST_FLOW_OK) {
|
if (result != GST_FLOW_OK) {
|
||||||
|
const gchar *flowname;
|
||||||
|
|
||||||
|
flowname = gst_flow_get_name (result);
|
||||||
|
|
||||||
queue->srcresult = result;
|
queue->srcresult = result;
|
||||||
if (GST_FLOW_IS_FATAL (result)) {
|
if (GST_FLOW_IS_FATAL (result)) {
|
||||||
GST_ELEMENT_ERROR (queue, STREAM, STOPPED,
|
GST_ELEMENT_ERROR (queue, STREAM, STOPPED,
|
||||||
("streaming stopped, reason %d", result),
|
("streaming stopped, reason %s", flowname),
|
||||||
("streaming stopped, reason %d", result));
|
("streaming stopped, reason %s", flowname));
|
||||||
gst_pad_push_event (queue->srcpad, gst_event_new (GST_EVENT_EOS));
|
gst_pad_push_event (queue->srcpad, gst_event_new (GST_EVENT_EOS));
|
||||||
}
|
}
|
||||||
|
GST_DEBUG ("pausing queue, reason %s", flowname);
|
||||||
gst_pad_pause_task (queue->srcpad);
|
gst_pad_pause_task (queue->srcpad);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -760,6 +785,7 @@ restart:
|
||||||
/* all incomming data is now unexpected */
|
/* all incomming data is now unexpected */
|
||||||
queue->srcresult = GST_FLOW_UNEXPECTED;
|
queue->srcresult = GST_FLOW_UNEXPECTED;
|
||||||
/* and we don't need to process anymore */
|
/* and we don't need to process anymore */
|
||||||
|
GST_DEBUG ("pausing queue, we're EOS now");
|
||||||
gst_pad_pause_task (queue->srcpad);
|
gst_pad_pause_task (queue->srcpad);
|
||||||
restart = FALSE;
|
restart = FALSE;
|
||||||
}
|
}
|
||||||
|
@ -780,8 +806,10 @@ restart:
|
||||||
|
|
||||||
out_flushing:
|
out_flushing:
|
||||||
{
|
{
|
||||||
|
const gchar *flowname = gst_flow_get_name (queue->srcresult);
|
||||||
|
|
||||||
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
GST_CAT_LOG_OBJECT (queue_dataflow, queue,
|
||||||
"exit because task paused, reason: %d", queue->srcresult);
|
"exit because task paused, reason: %s", flowname);
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
|
@ -890,7 +918,13 @@ gst_queue_src_activate_push (GstPad * pad, gboolean active)
|
||||||
if (active) {
|
if (active) {
|
||||||
GST_QUEUE_MUTEX_LOCK (queue);
|
GST_QUEUE_MUTEX_LOCK (queue);
|
||||||
queue->srcresult = GST_FLOW_OK;
|
queue->srcresult = GST_FLOW_OK;
|
||||||
|
/* we do not start the task yet if the pad is not connected */
|
||||||
|
if (gst_pad_is_linked (pad))
|
||||||
result = gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
result = gst_pad_start_task (pad, (GstTaskFunction) gst_queue_loop, pad);
|
||||||
|
else {
|
||||||
|
GST_DEBUG ("not starting task as pad is not linked");
|
||||||
|
result = TRUE;
|
||||||
|
}
|
||||||
GST_QUEUE_MUTEX_UNLOCK (queue);
|
GST_QUEUE_MUTEX_UNLOCK (queue);
|
||||||
} else {
|
} else {
|
||||||
/* step 1, unblock chain and loop functions */
|
/* step 1, unblock chain and loop functions */
|
||||||
|
|
Loading…
Reference in a new issue