mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-22 17:51:16 +00:00
docs/libs/gstreamer-libs-sections.txt: Added basesink new methods.
Original commit message from CVS: * docs/libs/gstreamer-libs-sections.txt: Added basesink new methods. * gst/gstevent.c: * gst/gstevent.h: Docs updates. Flesh out the QoS docs. * libs/gst/base/gstadapter.c: Small doc clarification about ownership and flushing. * libs/gst/base/gstbasesink.c: (gst_base_sink_set_sync), (gst_base_sink_get_sync), (gst_base_sink_set_max_lateness), (gst_base_sink_get_max_lateness), (gst_base_sink_set_property), (gst_base_sink_get_property), (gst_base_sink_do_sync): * libs/gst/base/gstbasesink.h: Added new methods to allow subclass to control max-lateness and sync. Generate very basic QoS events based on last sync observation. Updated docs, fix typo, added some QoS blurb. * libs/gst/base/gstbasesrc.c: Remove obsolete _get_state() calls from docs.
This commit is contained in:
parent
c45bd3fb9f
commit
7a88e2a762
8 changed files with 182 additions and 32 deletions
25
ChangeLog
25
ChangeLog
|
@ -1,3 +1,28 @@
|
|||
2006-03-07 Wim Taymans <wim@fluendo.com>
|
||||
|
||||
* docs/libs/gstreamer-libs-sections.txt:
|
||||
Added basesink new methods.
|
||||
|
||||
* gst/gstevent.c:
|
||||
* gst/gstevent.h:
|
||||
Docs updates. Flesh out the QoS docs.
|
||||
|
||||
* libs/gst/base/gstadapter.c:
|
||||
Small doc clarification about ownership and flushing.
|
||||
|
||||
* libs/gst/base/gstbasesink.c: (gst_base_sink_set_sync),
|
||||
(gst_base_sink_get_sync), (gst_base_sink_set_max_lateness),
|
||||
(gst_base_sink_get_max_lateness), (gst_base_sink_set_property),
|
||||
(gst_base_sink_get_property), (gst_base_sink_do_sync):
|
||||
* libs/gst/base/gstbasesink.h:
|
||||
Added new methods to allow subclass to control max-lateness
|
||||
and sync.
|
||||
Generate very basic QoS events based on last sync observation.
|
||||
Updated docs, fix typo, added some QoS blurb.
|
||||
|
||||
* libs/gst/base/gstbasesrc.c:
|
||||
Remove obsolete _get_state() calls from docs.
|
||||
|
||||
2006-03-07 Wim Taymans <wim@fluendo.com>
|
||||
|
||||
* docs/libs/gstreamer-libs-sections.txt:
|
||||
|
|
|
@ -159,6 +159,11 @@ GstBaseSink
|
|||
|
||||
GST_BASE_SINK_PAD
|
||||
|
||||
gst_base_sink_set_sync
|
||||
gst_base_sink_get_sync
|
||||
gst_base_sink_set_max_lateness
|
||||
gst_base_sink_get_max_lateness
|
||||
|
||||
<SUBSECTION Standard>
|
||||
GstBaseSinkClass
|
||||
GST_BASE_SINK
|
||||
|
|
|
@ -615,17 +615,28 @@ gst_event_parse_buffer_size (GstEvent * event, GstFormat * format,
|
|||
* Allocate a new qos event with the given values.
|
||||
* The QOS event is generated in an element that wants an upstream
|
||||
* element to either reduce or increase its rate because of
|
||||
* high/low CPU load.
|
||||
* high/low CPU load or other resource usage such as network performance.
|
||||
*
|
||||
* proportion is the requested adjustment in datarate, 1.0 is the normal
|
||||
* @proportion is the requested adjustment in datarate, 1.0 is the normal
|
||||
* datarate, 0.75 means increase datarate by 75%, 1.5 is 150%. Negative
|
||||
* values request a slow down, so -0.75 means a decrease by 75%.
|
||||
*
|
||||
* diff is the difference against the clock in stream time of the last
|
||||
* @diff is the difference against the clock in stream time of the last
|
||||
* buffer that caused the element to generate the QOS event.
|
||||
*
|
||||
* timestamp is the timestamp of the last buffer that cause the element
|
||||
* to generate the QOS event.
|
||||
* @timestamp is the timestamp of the last buffer that cause the element
|
||||
* to generate the QOS event.
|
||||
*
|
||||
* The upstream element can use the @diff and @timestamp values to decide
|
||||
* whether to process more buffers. All buffers with timestamp <=
|
||||
* @timestamp + @diff will certainly arrive late in the sink as well.
|
||||
*
|
||||
* The @proportion value is generally computed based on more long
|
||||
* term statistics about the stream quality and can be used in various ways
|
||||
* such as lowering or increasing processing quality.
|
||||
*
|
||||
* The application can use general event probes to intercept the QoS
|
||||
* event and implement custom application specific QoS handling.
|
||||
*
|
||||
* Returns: A new QOS event.
|
||||
*/
|
||||
|
|
|
@ -378,7 +378,6 @@ void gst_event_parse_buffer_size (GstEvent *event, GstFormat *format, gint64 *
|
|||
gint64 *maxsize, gboolean *async);
|
||||
|
||||
/* QOS events */
|
||||
/* FIXME: QOS events need to be fully specified and implemented */
|
||||
GstEvent* gst_event_new_qos (gdouble proportion, GstClockTimeDiff diff,
|
||||
GstClockTime timestamp);
|
||||
void gst_event_parse_qos (GstEvent *event, gdouble *proportion, GstClockTimeDiff *diff,
|
||||
|
|
|
@ -67,6 +67,9 @@
|
|||
* gst_adapter_clear(). Data should also be cleared or processed on EOS and
|
||||
* when changing state from #GST_STATE_PAUSED to #GST_STATE_READY.
|
||||
*
|
||||
* Also check the GST_BUFFER_FLAG_DISCONT flag on the buffer. Some elements might
|
||||
* need to clear the adapter after a discontinuity.
|
||||
*
|
||||
* A last thing to note is that while GstAdapter is pretty optimized,
|
||||
* merging buffers still might be an operation that requires a memcpy()
|
||||
* operation, and this operation is not the fastest. Because of this, some
|
||||
|
@ -76,11 +79,14 @@
|
|||
* GstAdapter is not MT safe. All operations on an adapter must be serialized by
|
||||
* the caller. This is not normally a problem, however, as the normal use case
|
||||
* of GstAdapter is inside one pad's chain function, in which case access is
|
||||
* serialized via the pad's stream lock.
|
||||
* serialized via the pad's STREAM_LOCK.
|
||||
*
|
||||
* Note that gst_adapter_push() takes ownership of the buffer passed.
|
||||
* Note that gst_adapter_push() takes ownership of the buffer passed. Use
|
||||
* gst_buffer_ref() before pushing it into the adapter if you still want to
|
||||
* access the buffer later. The adapter will never modify the data in the
|
||||
* buffer pushed in it.
|
||||
*
|
||||
* Last reviewed on 2005-12-18 (0.10.0).
|
||||
* Last reviewed on 2006-03-07 (0.10.4).
|
||||
*/
|
||||
|
||||
#include <string.h>
|
||||
|
|
|
@ -30,7 +30,7 @@
|
|||
* you, for example preroll, clock synchronization, state changes, activation in
|
||||
* push or pull mode, and queries. In most cases, when writing sink elements,
|
||||
* there is no need to implement class methods from #GstElement or to set
|
||||
* functions on pads, because the #GstBaseSink infrastructure is sufficient.
|
||||
* functions on pads, because the #GstBaseSink infrastructure should be sufficient.
|
||||
*
|
||||
* There is only support in GstBaseSink for one sink pad, which should be named
|
||||
* "sink". A sink implementation (subclass of GstBaseSink) should install a pad
|
||||
|
@ -53,8 +53,8 @@
|
|||
* #GstBaseSink will handle the prerolling correctly. This means that it will
|
||||
* return GST_STATE_CHANGE_ASYNC from a state change to PAUSED until the first buffer
|
||||
* arrives in this element. The base class will call the GstBaseSink::preroll
|
||||
* vmethod with this preroll buffer and will then commit the state change to
|
||||
* PAUSED.
|
||||
* vmethod with this preroll buffer and will then commit the state change to the
|
||||
* next asynchronously pending state.
|
||||
*
|
||||
* When the element is set to PLAYING, #GstBaseSink will synchronize on the clock
|
||||
* using the times returned from ::get_times. If this function returns
|
||||
|
@ -88,7 +88,7 @@
|
|||
* query will be forwarded upstream.
|
||||
*
|
||||
* The ::set_caps function will be called when the subclass should configure itself
|
||||
* to precess a specific media type.
|
||||
* to process a specific media type.
|
||||
*
|
||||
* The ::start and ::stop virtual methods will be called when resources should be
|
||||
* allocated. Any ::preroll, ::render and ::set_caps function will be called
|
||||
|
@ -106,7 +106,16 @@
|
|||
* operations they perform in the ::render method. This is mostly usefull when
|
||||
* the ::render method performs a blocking write on a file descripter.
|
||||
*
|
||||
* Last reviewed on 2006-01-30 (0.10.3)
|
||||
* The max-lateness property defines how the sink deals with buffers that arrive
|
||||
* too late in the sink. A buffer arrives too late in the sink when the presentation
|
||||
* time (as a combination of the last segment, buffer timestamp and element
|
||||
* base_time) is before the current time of the clock. If the frame is later than
|
||||
* max-lateness, the sink will drop the buffer and will generate a QoS event upstream.
|
||||
* This feature is disabled if sync is disabled, the ::get-times method does not
|
||||
* return a valid start time or max-lateness is set to -1 (the default).
|
||||
* Subclasses can use gst_base_sink_set_max_lateness() to configure the max-lateness.
|
||||
*
|
||||
* Last reviewed on 2006-03-07 (0.10.4)
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
|
@ -375,6 +384,95 @@ gst_base_sink_finalize (GObject * object)
|
|||
G_OBJECT_CLASS (parent_class)->finalize (object);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_base_sink_set_sync:
|
||||
* @sink: the sink
|
||||
* @sync: the new sync value.
|
||||
*
|
||||
* Configures @sink to synchronize on the clock or not. When
|
||||
* @sync is FALSE, incomming samples will be played as fast as
|
||||
* possible. If @sync is TRUE, the timestamps of the incomming
|
||||
* buffers will be used to schedule the exact render time of its
|
||||
* contents.
|
||||
*
|
||||
* Since: 0.10.4
|
||||
*/
|
||||
void
|
||||
gst_base_sink_set_sync (GstBaseSink * sink, gboolean sync)
|
||||
{
|
||||
GST_OBJECT_LOCK (sink);
|
||||
sink->sync = sync;
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_base_sink_get_sync:
|
||||
* @sink: the sink
|
||||
*
|
||||
* Checks if @sink is currently configured to synchronize against the
|
||||
* clock.
|
||||
*
|
||||
* Returns: TRUE if the sink is configured to synchronize against the clock.
|
||||
*
|
||||
* Since: 0.10.4
|
||||
*/
|
||||
gboolean
|
||||
gst_base_sink_get_sync (GstBaseSink * sink)
|
||||
{
|
||||
gboolean res;
|
||||
|
||||
GST_OBJECT_LOCK (sink);
|
||||
res = sink->sync;
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_base_sink_set_max_lateness:
|
||||
* @sink: the sink
|
||||
* @max_lateness: the new max lateness value.
|
||||
*
|
||||
* Sets the new max lateness value to @max_lateness. This value is
|
||||
* used to decide if a buffer should be dropped or not based on the
|
||||
* buffer timestamp and the current clock time. A value of -1 means
|
||||
* an unlimited time.
|
||||
*
|
||||
* Since: 0.10.4
|
||||
*/
|
||||
void
|
||||
gst_base_sink_set_max_lateness (GstBaseSink * sink, gint64 max_lateness)
|
||||
{
|
||||
GST_OBJECT_LOCK (sink);
|
||||
sink->abidata.ABI.max_lateness = max_lateness;
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_base_sink_get_max_lateness:
|
||||
* @sink: the sink
|
||||
*
|
||||
* Gets the max lateness value. See gst_base_sink_set_max_lateness for
|
||||
* more details.
|
||||
*
|
||||
* Returns: The maximum time in nanoseconds that a buffer can be late
|
||||
* before it is dropped and not rendered. A value of -1 means an
|
||||
* unlimited time.
|
||||
*
|
||||
* Since: 0.10.4
|
||||
*/
|
||||
gint64
|
||||
gst_base_sink_get_max_lateness (GstBaseSink * sink)
|
||||
{
|
||||
gint64 res;
|
||||
|
||||
GST_OBJECT_LOCK (sink);
|
||||
res = sink->abidata.ABI.max_lateness;
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
static void
|
||||
gst_base_sink_set_property (GObject * object, guint prop_id,
|
||||
const GValue * value, GParamSpec * pspec)
|
||||
|
@ -389,14 +487,10 @@ gst_base_sink_set_property (GObject * object, guint prop_id,
|
|||
GST_PAD_PREROLL_UNLOCK (sink->sinkpad);
|
||||
break;
|
||||
case PROP_SYNC:
|
||||
GST_OBJECT_LOCK (sink);
|
||||
sink->sync = g_value_get_boolean (value);
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
gst_base_sink_set_sync (sink, g_value_get_boolean (value));
|
||||
break;
|
||||
case PROP_MAX_LATENESS:
|
||||
GST_OBJECT_LOCK (sink);
|
||||
sink->abidata.ABI.max_lateness = g_value_get_int64 (value);
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
gst_base_sink_set_max_lateness (sink, g_value_get_int64 (value));
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
|
@ -417,14 +511,10 @@ gst_base_sink_get_property (GObject * object, guint prop_id, GValue * value,
|
|||
GST_PAD_PREROLL_UNLOCK (sink->sinkpad);
|
||||
break;
|
||||
case PROP_SYNC:
|
||||
GST_OBJECT_LOCK (sink);
|
||||
g_value_set_boolean (value, sink->sync);
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
g_value_set_boolean (value, gst_base_sink_get_sync (sink));
|
||||
break;
|
||||
case PROP_MAX_LATENESS:
|
||||
GST_OBJECT_LOCK (sink);
|
||||
g_value_set_int64 (value, sink->abidata.ABI.max_lateness);
|
||||
GST_OBJECT_UNLOCK (sink);
|
||||
g_value_set_int64 (value, gst_base_sink_get_max_lateness (sink));
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
|
@ -432,6 +522,7 @@ gst_base_sink_get_property (GObject * object, guint prop_id, GValue * value,
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
static GstCaps *
|
||||
gst_base_sink_get_caps (GstBaseSink * sink)
|
||||
{
|
||||
|
@ -838,14 +929,23 @@ again:
|
|||
|
||||
*late = FALSE;
|
||||
|
||||
if (basesink->abidata.ABI.max_lateness != -1) {
|
||||
if (status == GST_CLOCK_EARLY
|
||||
/* FIXME, update clock stats here and do some QoS */
|
||||
if (status == GST_CLOCK_EARLY) {
|
||||
if (basesink->abidata.ABI.max_lateness != -1
|
||||
&& jitter > basesink->abidata.ABI.max_lateness) {
|
||||
/* FIXME, update clock stats here and do some QoS */
|
||||
GstEvent *event;
|
||||
|
||||
GST_DEBUG_OBJECT (basesink, "late: jitter!! %" G_GINT64_FORMAT "\n",
|
||||
jitter);
|
||||
*late = TRUE;
|
||||
|
||||
/* generate QoS event, FIXME, calculate decent proportion. */
|
||||
event = gst_event_new_qos (-1.0, jitter, start);
|
||||
|
||||
/* send upstream */
|
||||
gst_pad_push_event (basesink->sinkpad, event);
|
||||
}
|
||||
} else {
|
||||
}
|
||||
|
||||
return GST_FLOW_OK;
|
||||
|
|
|
@ -136,6 +136,12 @@ struct _GstBaseSinkClass {
|
|||
|
||||
GType gst_base_sink_get_type(void);
|
||||
|
||||
void gst_base_sink_set_sync (GstBaseSink *sink, gboolean sync);
|
||||
gboolean gst_base_sink_get_sync (GstBaseSink *sink);
|
||||
|
||||
void gst_base_sink_set_max_lateness (GstBaseSink *sink, gint64 max_lateness);
|
||||
gint64 gst_base_sink_get_max_lateness (GstBaseSink *sink);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __GST_BASE_SINK_H__ */
|
||||
|
|
|
@ -135,7 +135,6 @@
|
|||
* ...
|
||||
* // stop recording
|
||||
* gst_element_set_state (audio_source, GST_STATE_NULL);
|
||||
* gst_element_get_state (audio_source, NULL, NULL, -1);
|
||||
* gst_element_set_locked_state (audio_source, TRUE);
|
||||
* ...
|
||||
* </programlisting>
|
||||
|
@ -146,13 +145,12 @@
|
|||
* ...
|
||||
* // everything done - shut down pipeline
|
||||
* gst_element_set_state (pipeline, GST_STATE_NULL);
|
||||
* gst_element_get_state (pipeline, NULL, NULL, -1);
|
||||
* gst_element_set_locked_state (audio_source, FALSE);
|
||||
* ...
|
||||
* </programlisting>
|
||||
* </para>
|
||||
* <para>
|
||||
* Last reviewed on 2005-12-18 (0.10.0)
|
||||
* Last reviewed on 2006-03-07 (0.10.4)
|
||||
* </para>
|
||||
* </refsect2>
|
||||
*/
|
||||
|
|
Loading…
Reference in a new issue