gstreamer_core/libs/gst/base/gstbasesrc.c
changeset 0 0e761a78d257
child 8 4a7fac7dd34a
equal deleted inserted replaced
-1:000000000000 0:0e761a78d257
       
     1 /* GStreamer
       
     2  * Copyright (C) 1999,2000 Erik Walthinsen <omega@cse.ogi.edu>
       
     3  *               2000,2005 Wim Taymans <wim@fluendo.com>
       
     4  *
       
     5  * gstbasesrc.c:
       
     6  *
       
     7  * This library is free software; you can redistribute it and/or
       
     8  * modify it under the terms of the GNU Library General Public
       
     9  * License as published by the Free Software Foundation; either
       
    10  * version 2 of the License, or (at your option) any later version.
       
    11  *
       
    12  * This library is distributed in the hope that it will be useful,
       
    13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
       
    14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
       
    15  * Library General Public License for more details.
       
    16  *
       
    17  * You should have received a copy of the GNU Library General Public
       
    18  * License along with this library; if not, write to the
       
    19  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
       
    20  * Boston, MA 02111-1307, USA.
       
    21  */
       
    22 
       
    23 /**
       
    24  * SECTION:gstbasesrc
       
    25  * @short_description: Base class for getrange based source elements
       
    26  * @see_also: #GstPushSrc, #GstBaseTransform, #GstBaseSink
       
    27  *
       
    28  * This is a generice base class for source elements. The following
       
    29  * types of sources are supported:
       
    30  * <itemizedlist>
       
    31  *   <listitem><para>random access sources like files</para></listitem>
       
    32  *   <listitem><para>seekable sources</para></listitem>
       
    33  *   <listitem><para>live sources</para></listitem>
       
    34  * </itemizedlist>
       
    35  *
       
    36  * <refsect2>
       
    37  * <para>
       
    38  * The source can be configured to operate in any #GstFormat with the
       
    39  * gst_base_src_set_format() method. The currently set format determines 
       
    40  * the format of the internal #GstSegment and any #GST_EVENT_NEWSEGMENT 
       
    41  * events. The default format for #GstBaseSrc is #GST_FORMAT_BYTES.
       
    42  * </para>
       
    43  * <para>
       
    44  * #GstBaseSrc always supports push mode scheduling. If the following
       
    45  * conditions are met, it also supports pull mode scheduling:
       
    46  * <itemizedlist>
       
    47  *   <listitem><para>The format is set to #GST_FORMAT_BYTES (default).</para>
       
    48  *   </listitem>
       
    49  *   <listitem><para>#GstBaseSrc::is_seekable returns %TRUE.</para>
       
    50  *   </listitem>
       
    51  * </itemizedlist>
       
    52  * </para>
       
    53  * <para>
       
    54  * Since 0.10.9, any #GstBaseSrc can enable pull based scheduling at any 
       
    55  * time by overriding #GstBaseSrc::check_get_range so that it returns %TRUE. 
       
    56  * </para>
       
    57  * <para>
       
    58  * If all the conditions are met for operating in pull mode, #GstBaseSrc is
       
    59  * automatically seekable in push mode as well. The following conditions must 
       
    60  * be met to make the element seekable in push mode when the format is not
       
    61  * #GST_FORMAT_BYTES:
       
    62  * <itemizedlist>
       
    63  *   <listitem><para>
       
    64  *     #GstBaseSrc::is_seekable returns %TRUE.
       
    65  *   </para></listitem>
       
    66  *   <listitem><para>
       
    67  *     #GstBaseSrc::query can convert all supported seek formats to the
       
    68  *     internal format as set with gst_base_src_set_format().
       
    69  *   </para></listitem>
       
    70  *   <listitem><para>
       
    71  *     #GstBaseSrc::do_seek is implemented, performs the seek and returns %TRUE.
       
    72  *   </para></listitem>
       
    73  * </itemizedlist>
       
    74  * </para>
       
    75  * <para>
       
    76  * When the element does not meet the requirements to operate in pull mode,
       
    77  * the offset and length in the #GstBaseSrc::create method should be ignored.
       
    78  * It is recommended to subclass #GstPushSrc instead, in this situation. If the
       
    79  * element can operate in pull mode but only with specific offsets and
       
    80  * lengths, it is allowed to generate an error when the wrong values are passed
       
    81  * to the #GstBaseSrc::create function.
       
    82  * </para>
       
    83  * <para>
       
    84  * #GstBaseSrc has support for live sources. Live sources are sources that when
       
    85  * paused discard data, such as audio or video capture devices. A typical live
       
    86  * source also produces data at a fixed rate and thus provides a clock to publish
       
    87  * this rate.
       
    88  * Use gst_base_src_set_live() to activate the live source mode.
       
    89  * </para>
       
    90  * <para>
       
    91  * A live source does not produce data in the PAUSED state. This means that the 
       
    92  * #GstBaseSrc::create method will not be called in PAUSED but only in PLAYING.
       
    93  * To signal the pipeline that the element will not produce data, the return
       
    94  * value from the READY to PAUSED state will be #GST_STATE_CHANGE_NO_PREROLL.
       
    95  * </para>
       
    96  * <para>
       
    97  * A typical live source will timestamp the buffers it creates with the 
       
    98  * current running time of the pipeline. This is one reason why a live source
       
    99  * can only produce data in the PLAYING state, when the clock is actually 
       
   100  * distributed and running. 
       
   101  * </para>
       
   102  * <para>
       
   103  * Live sources that synchronize and block on the clock (an audio source, for
       
   104  * example) can since 0.10.12 use gst_base_src_wait_playing() when the ::create
       
   105  * function was interrupted by a state change to PAUSED.
       
   106  * </para>
       
   107  * <para>
       
   108  * The #GstBaseSrc::get_times method can be used to implement pseudo-live 
       
   109  * sources.
       
   110  * It only makes sense to implement the ::get_times function if the source is 
       
   111  * a live source. The ::get_times function should return timestamps starting
       
   112  * from 0, as if it were a non-live source. The base class will make sure that
       
   113  * the timestamps are transformed into the current running_time.
       
   114  * The base source will then wait for the calculated running_time before pushing
       
   115  * out the buffer.
       
   116  * </para>
       
   117  * <para>
       
   118  * For live sources, the base class will by default report a latency of 0.
       
   119  * For pseudo live sources, the base class will by default measure the difference
       
   120  * between the first buffer timestamp and the start time of get_times and will
       
   121  * report this value as the latency. 
       
   122  * Subclasses should override the query function when this behaviour is not
       
   123  * acceptable.
       
   124  * </para>
       
   125  * <para>
       
   126  * There is only support in #GstBaseSrc for exactly one source pad, which 
       
   127  * should be named "src". A source implementation (subclass of #GstBaseSrc) 
       
   128  * should install a pad template in its class_init function, like so:
       
   129  * </para>
       
   130  * <para>
       
   131  * <programlisting>
       
   132  * static void
       
   133  * my_element_class_init (GstMyElementClass *klass)
       
   134  * {
       
   135  *   GstElementClass *gstelement_class = GST_ELEMENT_CLASS (klass);
       
   136  *   // srctemplate should be a #GstStaticPadTemplate with direction
       
   137  *   // #GST_PAD_SRC and name "src"
       
   138  *   gst_element_class_add_pad_template (gstelement_class,
       
   139  *       gst_static_pad_template_get (&amp;srctemplate));
       
   140  *   // see #GstElementDetails
       
   141  *   gst_element_class_set_details (gstelement_class, &amp;details);
       
   142  * }
       
   143  * </programlisting>
       
   144  * </para>
       
   145  * <title>Controlled shutdown of live sources in applications</title>
       
   146  * <para>
       
   147  * Applications that record from a live source may want to stop recording
       
   148  * in a controlled way, so that the recording is stopped, but the data
       
   149  * already in the pipeline is processed to the end (remember that many live
       
   150  * sources would go on recording forever otherwise). For that to happen the
       
   151  * application needs to make the source stop recording and send an EOS
       
   152  * event down the pipeline. The application would then wait for an
       
   153  * EOS message posted on the pipeline's bus to know when all data has
       
   154  * been processed and the pipeline can safely be stopped.
       
   155  * </para>
       
   156  * <para>
       
   157  * Since GStreamer 0.10.16 an application may send an EOS event to a source
       
   158  * element to make it send an EOS event downstream. This can typically be done
       
   159  * with the gst_element_send_event() function on the element or its parent bin.
       
   160  * </para>
       
   161  * <para>
       
   162  * After the EOS has been sent to the element, the application should wait for
       
   163  * an EOS message to be posted on the pipeline's bus. Once this EOS message is
       
   164  * received, it may safely shut down the entire pipeline.
       
   165  * </para>
       
   166  * <para>
       
   167  * The old behaviour for controlled shutdown introduced since GStreamer 0.10.3
       
   168  * is still available but deprecated as it is dangerous and less flexible.
       
   169  * </para>
       
   170  * <para>
       
   171  * Last reviewed on 2007-12-19 (0.10.16)
       
   172  * </para>
       
   173  * </refsect2>
       
   174  */
       
   175 
       
   176 #ifdef HAVE_CONFIG_H
       
   177 #  include "config.h"
       
   178 #endif
       
   179 
       
   180 #ifdef __SYMBIAN32__
       
   181 #include <gst_global.h>
       
   182 #endif
       
   183 #include <stdlib.h>
       
   184 #include <string.h>
       
   185 
       
   186 #include "gstbasesrc.h"
       
   187 #include "gsttypefindhelper.h"
       
   188 #include <gst/gstmarshal.h>
       
   189 #include <gst/gst-i18n-lib.h>
       
   190 
       
   191 #ifdef __SYMBIAN32__
       
   192 #include <glib_global.h>
       
   193 #include <gobject_global.h>
       
   194 #endif
       
   195 GST_DEBUG_CATEGORY_STATIC (gst_base_src_debug);
       
   196 #ifndef __SYMBIAN32__
       
   197 #define GST_CAT_DEFAULT gst_base_src_debug
       
   198 #endif
       
   199 
       
   200 #define GST_LIVE_GET_LOCK(elem)               (GST_BASE_SRC_CAST(elem)->live_lock)
       
   201 #define GST_LIVE_LOCK(elem)                   g_mutex_lock(GST_LIVE_GET_LOCK(elem))
       
   202 #define GST_LIVE_TRYLOCK(elem)                g_mutex_trylock(GST_LIVE_GET_LOCK(elem))
       
   203 #define GST_LIVE_UNLOCK(elem)                 g_mutex_unlock(GST_LIVE_GET_LOCK(elem))
       
   204 #define GST_LIVE_GET_COND(elem)               (GST_BASE_SRC_CAST(elem)->live_cond)
       
   205 #define GST_LIVE_WAIT(elem)                   g_cond_wait (GST_LIVE_GET_COND (elem), GST_LIVE_GET_LOCK (elem))
       
   206 #define GST_LIVE_TIMED_WAIT(elem, timeval)    g_cond_timed_wait (GST_LIVE_GET_COND (elem), GST_LIVE_GET_LOCK (elem),\
       
   207                                                                                 timeval)
       
   208 #define GST_LIVE_SIGNAL(elem)                 g_cond_signal (GST_LIVE_GET_COND (elem));
       
   209 #define GST_LIVE_BROADCAST(elem)              g_cond_broadcast (GST_LIVE_GET_COND (elem));
       
   210 
       
   211 /* BaseSrc signals and args */
       
   212 enum
       
   213 {
       
   214   /* FILL ME */
       
   215   LAST_SIGNAL
       
   216 };
       
   217 
       
   218 #define DEFAULT_BLOCKSIZE       4096
       
   219 #define DEFAULT_NUM_BUFFERS     -1
       
   220 #define DEFAULT_TYPEFIND	FALSE
       
   221 #define DEFAULT_DO_TIMESTAMP	FALSE
       
   222 
       
   223 enum
       
   224 {
       
   225   PROP_0,
       
   226   PROP_BLOCKSIZE,
       
   227   PROP_NUM_BUFFERS,
       
   228   PROP_TYPEFIND,
       
   229   PROP_DO_TIMESTAMP
       
   230 };
       
   231 
       
   232 #define GST_BASE_SRC_GET_PRIVATE(obj)  \
       
   233    (G_TYPE_INSTANCE_GET_PRIVATE ((obj), GST_TYPE_BASE_SRC, GstBaseSrcPrivate))
       
   234 
       
   235 struct _GstBaseSrcPrivate
       
   236 {
       
   237   gboolean last_sent_eos;       /* last thing we did was send an EOS (we set this
       
   238                                  * to avoid the sending of two EOS in some cases) */
       
   239   gboolean discont;
       
   240   gboolean flushing;
       
   241 
       
   242   /* two segments to be sent in the streaming thread with STREAM_LOCK */
       
   243   GstEvent *close_segment;
       
   244   GstEvent *start_segment;
       
   245 
       
   246   /* if EOS is pending */
       
   247   gboolean pending_eos;
       
   248 
       
   249   /* startup latency is the time it takes between going to PLAYING and producing
       
   250    * the first BUFFER with running_time 0. This value is included in the latency
       
   251    * reporting. */
       
   252   GstClockTime latency;
       
   253   /* timestamp offset, this is the offset add to the values of gst_times for
       
   254    * pseudo live sources */
       
   255   GstClockTimeDiff ts_offset;
       
   256 
       
   257   gboolean do_timestamp;
       
   258 };
       
   259 
       
   260 static GstElementClass *parent_class = NULL;
       
   261 
       
   262 static void gst_base_src_base_init (gpointer g_class);
       
   263 static void gst_base_src_class_init (GstBaseSrcClass * klass);
       
   264 static void gst_base_src_init (GstBaseSrc * src, gpointer g_class);
       
   265 static void gst_base_src_finalize (GObject * object);
       
   266 #ifdef __SYMBIAN32__
       
   267 EXPORT_C
       
   268 #endif
       
   269 
       
   270 
       
   271 
       
   272 GType
       
   273 gst_base_src_get_type (void)
       
   274 {
       
   275   static GType base_src_type = 0;
       
   276 
       
   277   if (G_UNLIKELY (base_src_type == 0)) {
       
   278     static const GTypeInfo base_src_info = {
       
   279       sizeof (GstBaseSrcClass),
       
   280       (GBaseInitFunc) gst_base_src_base_init,
       
   281       NULL,
       
   282       (GClassInitFunc) gst_base_src_class_init,
       
   283       NULL,
       
   284       NULL,
       
   285       sizeof (GstBaseSrc),
       
   286       0,
       
   287       (GInstanceInitFunc) gst_base_src_init,
       
   288     };
       
   289 
       
   290     base_src_type = g_type_register_static (GST_TYPE_ELEMENT,
       
   291         "GstBaseSrc", &base_src_info, G_TYPE_FLAG_ABSTRACT);
       
   292   }
       
   293   return base_src_type;
       
   294 }
       
   295 static GstCaps *gst_base_src_getcaps (GstPad * pad);
       
   296 static gboolean gst_base_src_setcaps (GstPad * pad, GstCaps * caps);
       
   297 static void gst_base_src_fixate (GstPad * pad, GstCaps * caps);
       
   298 
       
   299 static gboolean gst_base_src_activate_push (GstPad * pad, gboolean active);
       
   300 static gboolean gst_base_src_activate_pull (GstPad * pad, gboolean active);
       
   301 static void gst_base_src_set_property (GObject * object, guint prop_id,
       
   302     const GValue * value, GParamSpec * pspec);
       
   303 static void gst_base_src_get_property (GObject * object, guint prop_id,
       
   304     GValue * value, GParamSpec * pspec);
       
   305 static gboolean gst_base_src_event_handler (GstPad * pad, GstEvent * event);
       
   306 static gboolean gst_base_src_send_event (GstElement * elem, GstEvent * event);
       
   307 static gboolean gst_base_src_default_event (GstBaseSrc * src, GstEvent * event);
       
   308 static const GstQueryType *gst_base_src_get_query_types (GstElement * element);
       
   309 
       
   310 static gboolean gst_base_src_query (GstPad * pad, GstQuery * query);
       
   311 
       
   312 static gboolean gst_base_src_default_negotiate (GstBaseSrc * basesrc);
       
   313 static gboolean gst_base_src_default_do_seek (GstBaseSrc * src,
       
   314     GstSegment * segment);
       
   315 static gboolean gst_base_src_default_query (GstBaseSrc * src, GstQuery * query);
       
   316 static gboolean gst_base_src_default_prepare_seek_segment (GstBaseSrc * src,
       
   317     GstEvent * event, GstSegment * segment);
       
   318 
       
   319 static gboolean gst_base_src_set_flushing (GstBaseSrc * basesrc,
       
   320     gboolean flushing, gboolean live_play, gboolean unlock, gboolean * playing);
       
   321 static gboolean gst_base_src_start (GstBaseSrc * basesrc);
       
   322 static gboolean gst_base_src_stop (GstBaseSrc * basesrc);
       
   323 
       
   324 static GstStateChangeReturn gst_base_src_change_state (GstElement * element,
       
   325     GstStateChange transition);
       
   326 
       
   327 static void gst_base_src_loop (GstPad * pad);
       
   328 static gboolean gst_base_src_pad_check_get_range (GstPad * pad);
       
   329 static gboolean gst_base_src_default_check_get_range (GstBaseSrc * bsrc);
       
   330 static GstFlowReturn gst_base_src_pad_get_range (GstPad * pad, guint64 offset,
       
   331     guint length, GstBuffer ** buf);
       
   332 static GstFlowReturn gst_base_src_get_range (GstBaseSrc * src, guint64 offset,
       
   333     guint length, GstBuffer ** buf);
       
   334 
       
   335 static void
       
   336 gst_base_src_base_init (gpointer g_class)
       
   337 {
       
   338   GST_DEBUG_CATEGORY_INIT (gst_base_src_debug, "basesrc", 0, "basesrc element");
       
   339 }
       
   340 
       
   341 static void
       
   342 gst_base_src_class_init (GstBaseSrcClass * klass)
       
   343 {
       
   344   GObjectClass *gobject_class;
       
   345   GstElementClass *gstelement_class;
       
   346 
       
   347   gobject_class = G_OBJECT_CLASS (klass);
       
   348   gstelement_class = GST_ELEMENT_CLASS (klass);
       
   349 
       
   350   g_type_class_add_private (klass, sizeof (GstBaseSrcPrivate));
       
   351 
       
   352   parent_class = g_type_class_peek_parent (klass);
       
   353 
       
   354   gobject_class->finalize = GST_DEBUG_FUNCPTR (gst_base_src_finalize);
       
   355   gobject_class->set_property = GST_DEBUG_FUNCPTR (gst_base_src_set_property);
       
   356   gobject_class->get_property = GST_DEBUG_FUNCPTR (gst_base_src_get_property);
       
   357 
       
   358   g_object_class_install_property (gobject_class, PROP_BLOCKSIZE,
       
   359       g_param_spec_ulong ("blocksize", "Block size",
       
   360           "Size in bytes to read per buffer (0 = default)", 0, G_MAXULONG,
       
   361           DEFAULT_BLOCKSIZE, G_PARAM_READWRITE));
       
   362   g_object_class_install_property (gobject_class, PROP_NUM_BUFFERS,
       
   363       g_param_spec_int ("num-buffers", "num-buffers",
       
   364           "Number of buffers to output before sending EOS", -1, G_MAXINT,
       
   365           DEFAULT_NUM_BUFFERS, G_PARAM_READWRITE));
       
   366   g_object_class_install_property (gobject_class, PROP_TYPEFIND,
       
   367       g_param_spec_boolean ("typefind", "Typefind",
       
   368           "Run typefind before negotiating", DEFAULT_TYPEFIND,
       
   369           G_PARAM_READWRITE));
       
   370   g_object_class_install_property (gobject_class, PROP_DO_TIMESTAMP,
       
   371       g_param_spec_boolean ("do-timestamp", "Do timestamp",
       
   372           "Apply current stream time to buffers", DEFAULT_DO_TIMESTAMP,
       
   373           G_PARAM_READWRITE));
       
   374 
       
   375   gstelement_class->change_state =
       
   376       GST_DEBUG_FUNCPTR (gst_base_src_change_state);
       
   377   gstelement_class->send_event = GST_DEBUG_FUNCPTR (gst_base_src_send_event);
       
   378   gstelement_class->get_query_types =
       
   379       GST_DEBUG_FUNCPTR (gst_base_src_get_query_types);
       
   380 
       
   381   klass->negotiate = GST_DEBUG_FUNCPTR (gst_base_src_default_negotiate);
       
   382   klass->event = GST_DEBUG_FUNCPTR (gst_base_src_default_event);
       
   383   klass->do_seek = GST_DEBUG_FUNCPTR (gst_base_src_default_do_seek);
       
   384   klass->query = GST_DEBUG_FUNCPTR (gst_base_src_default_query);
       
   385   klass->check_get_range =
       
   386       GST_DEBUG_FUNCPTR (gst_base_src_default_check_get_range);
       
   387   klass->prepare_seek_segment =
       
   388       GST_DEBUG_FUNCPTR (gst_base_src_default_prepare_seek_segment);
       
   389 }
       
   390 
       
   391 static void
       
   392 gst_base_src_init (GstBaseSrc * basesrc, gpointer g_class)
       
   393 {
       
   394   GstPad *pad;
       
   395   GstPadTemplate *pad_template;
       
   396 
       
   397   basesrc->priv = GST_BASE_SRC_GET_PRIVATE (basesrc);
       
   398 
       
   399   basesrc->is_live = FALSE;
       
   400   basesrc->live_lock = g_mutex_new ();
       
   401   basesrc->live_cond = g_cond_new ();
       
   402   basesrc->num_buffers = DEFAULT_NUM_BUFFERS;
       
   403   basesrc->num_buffers_left = -1;
       
   404 
       
   405   basesrc->can_activate_push = TRUE;
       
   406   basesrc->pad_mode = GST_ACTIVATE_NONE;
       
   407 
       
   408   pad_template =
       
   409       gst_element_class_get_pad_template (GST_ELEMENT_CLASS (g_class), "src");
       
   410   g_return_if_fail (pad_template != NULL);
       
   411 
       
   412   GST_DEBUG_OBJECT (basesrc, "creating src pad");
       
   413   pad = gst_pad_new_from_template (pad_template, "src");
       
   414 
       
   415   GST_DEBUG_OBJECT (basesrc, "setting functions on src pad");
       
   416   gst_pad_set_activatepush_function (pad,
       
   417       GST_DEBUG_FUNCPTR (gst_base_src_activate_push));
       
   418   gst_pad_set_activatepull_function (pad,
       
   419       GST_DEBUG_FUNCPTR (gst_base_src_activate_pull));
       
   420   gst_pad_set_event_function (pad,
       
   421       GST_DEBUG_FUNCPTR (gst_base_src_event_handler));
       
   422   gst_pad_set_query_function (pad, GST_DEBUG_FUNCPTR (gst_base_src_query));
       
   423   gst_pad_set_checkgetrange_function (pad,
       
   424       GST_DEBUG_FUNCPTR (gst_base_src_pad_check_get_range));
       
   425   gst_pad_set_getrange_function (pad,
       
   426       GST_DEBUG_FUNCPTR (gst_base_src_pad_get_range));
       
   427   gst_pad_set_getcaps_function (pad, GST_DEBUG_FUNCPTR (gst_base_src_getcaps));
       
   428   gst_pad_set_setcaps_function (pad, GST_DEBUG_FUNCPTR (gst_base_src_setcaps));
       
   429   gst_pad_set_fixatecaps_function (pad,
       
   430       GST_DEBUG_FUNCPTR (gst_base_src_fixate));
       
   431 
       
   432   /* hold pointer to pad */
       
   433   basesrc->srcpad = pad;
       
   434   GST_DEBUG_OBJECT (basesrc, "adding src pad");
       
   435   gst_element_add_pad (GST_ELEMENT (basesrc), pad);
       
   436 
       
   437   basesrc->blocksize = DEFAULT_BLOCKSIZE;
       
   438   basesrc->clock_id = NULL;
       
   439   /* we operate in BYTES by default */
       
   440   gst_base_src_set_format (basesrc, GST_FORMAT_BYTES);
       
   441   basesrc->data.ABI.typefind = DEFAULT_TYPEFIND;
       
   442   basesrc->priv->do_timestamp = DEFAULT_DO_TIMESTAMP;
       
   443 
       
   444   GST_OBJECT_FLAG_UNSET (basesrc, GST_BASE_SRC_STARTED);
       
   445 
       
   446   GST_DEBUG_OBJECT (basesrc, "init done");
       
   447 }
       
   448 
       
   449 static void
       
   450 gst_base_src_finalize (GObject * object)
       
   451 {
       
   452   GstBaseSrc *basesrc;
       
   453   GstEvent **event_p;
       
   454 
       
   455   basesrc = GST_BASE_SRC (object);
       
   456 
       
   457   g_mutex_free (basesrc->live_lock);
       
   458   g_cond_free (basesrc->live_cond);
       
   459 
       
   460   event_p = &basesrc->data.ABI.pending_seek;
       
   461   gst_event_replace (event_p, NULL);
       
   462 
       
   463   G_OBJECT_CLASS (parent_class)->finalize (object);
       
   464 }
       
   465 
       
   466 /**
       
   467  * gst_base_src_wait_playing:
       
   468  * @src: the src
       
   469  *
       
   470  * If the #GstBaseSrcClass::create method performs its own synchronisation against
       
   471  * the clock it must unblock when going from PLAYING to the PAUSED state and call
       
   472  * this method before continuing to produce the remaining data.
       
   473  *
       
   474  * This function will block until a state change to PLAYING happens (in which
       
   475  * case this function returns #GST_FLOW_OK) or the processing must be stopped due
       
   476  * to a state change to READY or a FLUSH event (in which case this function
       
   477  * returns #GST_FLOW_WRONG_STATE).
       
   478  *
       
   479  * Since: 0.10.12
       
   480  *
       
   481  * Returns: #GST_FLOW_OK if @src is PLAYING and processing can
       
   482  * continue. Any other return value should be returned from the create vmethod.
       
   483  */
       
   484 #ifdef __SYMBIAN32__
       
   485 EXPORT_C
       
   486 #endif
       
   487 
       
   488 GstFlowReturn
       
   489 gst_base_src_wait_playing (GstBaseSrc * src)
       
   490 {
       
   491   /* block until the state changes, or we get a flush, or something */
       
   492   GST_DEBUG_OBJECT (src, "live source waiting for running state");
       
   493   GST_LIVE_WAIT (src);
       
   494   if (src->priv->flushing)
       
   495     goto flushing;
       
   496   GST_DEBUG_OBJECT (src, "live source unlocked");
       
   497 
       
   498   return GST_FLOW_OK;
       
   499 
       
   500   /* ERRORS */
       
   501 flushing:
       
   502   {
       
   503     GST_DEBUG_OBJECT (src, "we are flushing");
       
   504     return GST_FLOW_WRONG_STATE;
       
   505   }
       
   506 }
       
   507 
       
   508 /**
       
   509  * gst_base_src_set_live:
       
   510  * @src: base source instance
       
   511  * @live: new live-mode
       
   512  *
       
   513  * If the element listens to a live source, @live should
       
   514  * be set to %TRUE. 
       
   515  *
       
   516  * A live source will not produce data in the PAUSED state and
       
   517  * will therefore not be able to participate in the PREROLL phase
       
   518  * of a pipeline. To signal this fact to the application and the 
       
   519  * pipeline, the state change return value of the live source will
       
   520  * be GST_STATE_CHANGE_NO_PREROLL.
       
   521  */
       
   522 #ifdef __SYMBIAN32__
       
   523 EXPORT_C
       
   524 #endif
       
   525 
       
   526 void
       
   527 gst_base_src_set_live (GstBaseSrc * src, gboolean live)
       
   528 {
       
   529   GST_OBJECT_LOCK (src);
       
   530   src->is_live = live;
       
   531   GST_OBJECT_UNLOCK (src);
       
   532 }
       
   533 
       
   534 /**
       
   535  * gst_base_src_is_live:
       
   536  * @src: base source instance
       
   537  *
       
   538  * Check if an element is in live mode.
       
   539  *
       
   540  * Returns: %TRUE if element is in live mode.
       
   541  */
       
   542 #ifdef __SYMBIAN32__
       
   543 EXPORT_C
       
   544 #endif
       
   545 
       
   546 gboolean
       
   547 gst_base_src_is_live (GstBaseSrc * src)
       
   548 {
       
   549   gboolean result;
       
   550 
       
   551   GST_OBJECT_LOCK (src);
       
   552   result = src->is_live;
       
   553   GST_OBJECT_UNLOCK (src);
       
   554 
       
   555   return result;
       
   556 }
       
   557 
       
   558 /**
       
   559  * gst_base_src_set_format:
       
   560  * @src: base source instance
       
   561  * @format: the format to use
       
   562  *
       
   563  * Sets the default format of the source. This will be the format used
       
   564  * for sending NEW_SEGMENT events and for performing seeks.
       
   565  *
       
   566  * If a format of GST_FORMAT_BYTES is set, the element will be able to
       
   567  * operate in pull mode if the #GstBaseSrc::is_seekable returns TRUE.
       
   568  *
       
   569  * Since: 0.10.1
       
   570  */
       
   571 #ifdef __SYMBIAN32__
       
   572 EXPORT_C
       
   573 #endif
       
   574 
       
   575 void
       
   576 gst_base_src_set_format (GstBaseSrc * src, GstFormat format)
       
   577 {
       
   578   gst_segment_init (&src->segment, format);
       
   579 }
       
   580 
       
   581 /**
       
   582  * gst_base_src_query_latency:
       
   583  * @src: the source
       
   584  * @live: if the source is live
       
   585  * @min_latency: the min latency of the source
       
   586  * @max_latency: the max latency of the source
       
   587  *
       
   588  * Query the source for the latency parameters. @live will be TRUE when @src is
       
   589  * configured as a live source. @min_latency will be set to the difference
       
   590  * between the running time and the timestamp of the first buffer.
       
   591  * @max_latency is always the undefined value of -1.
       
   592  *
       
   593  * This function is mostly used by subclasses. 
       
   594  *
       
   595  * Returns: TRUE if the query succeeded.
       
   596  *
       
   597  * Since: 0.10.13
       
   598  */
       
   599 #ifdef __SYMBIAN32__
       
   600 EXPORT_C
       
   601 #endif
       
   602 
       
   603 gboolean
       
   604 gst_base_src_query_latency (GstBaseSrc * src, gboolean * live,
       
   605     GstClockTime * min_latency, GstClockTime * max_latency)
       
   606 {
       
   607   GstClockTime min;
       
   608 
       
   609   GST_OBJECT_LOCK (src);
       
   610   if (live)
       
   611     *live = src->is_live;
       
   612 
       
   613   /* if we have a startup latency, report this one, else report 0. Subclasses
       
   614    * are supposed to override the query function if they want something
       
   615    * else. */
       
   616   if (src->priv->latency != -1)
       
   617     min = src->priv->latency;
       
   618   else
       
   619     min = 0;
       
   620 
       
   621   if (min_latency)
       
   622     *min_latency = min;
       
   623   if (max_latency)
       
   624     *max_latency = -1;
       
   625 
       
   626   GST_LOG_OBJECT (src, "latency: live %d, min %" GST_TIME_FORMAT
       
   627       ", max %" GST_TIME_FORMAT, src->is_live, GST_TIME_ARGS (min),
       
   628       GST_TIME_ARGS (-1));
       
   629   GST_OBJECT_UNLOCK (src);
       
   630 
       
   631   return TRUE;
       
   632 }
       
   633 
       
   634 /**
       
   635  * gst_base_src_set_do_timestamp:
       
   636  * @src: the source
       
   637  * @timestamp: enable or disable timestamping
       
   638  *
       
   639  * Configure @src to automatically timestamp outgoing buffers based on the
       
   640  * current running_time of the pipeline. This property is mostly useful for live
       
   641  * sources.
       
   642  *
       
   643  * Since: 0.10.15
       
   644  */
       
   645 #ifdef __SYMBIAN32__
       
   646 EXPORT_C
       
   647 #endif
       
   648 
       
   649 void
       
   650 gst_base_src_set_do_timestamp (GstBaseSrc * src, gboolean timestamp)
       
   651 {
       
   652   GST_OBJECT_LOCK (src);
       
   653   src->priv->do_timestamp = timestamp;
       
   654   GST_OBJECT_UNLOCK (src);
       
   655 }
       
   656 
       
   657 /**
       
   658  * gst_base_src_get_do_timestamp:
       
   659  * @src: the source
       
   660  *
       
   661  * Query if @src timestamps outgoing buffers based on the current running_time.
       
   662  *
       
   663  * Returns: %TRUE if the base class will automatically timestamp outgoing buffers.
       
   664  *
       
   665  * Since: 0.10.15
       
   666  */
       
   667 #ifdef __SYMBIAN32__
       
   668 EXPORT_C
       
   669 #endif
       
   670 
       
   671 gboolean
       
   672 gst_base_src_get_do_timestamp (GstBaseSrc * src)
       
   673 {
       
   674   gboolean res;
       
   675 
       
   676   GST_OBJECT_LOCK (src);
       
   677   res = src->priv->do_timestamp;
       
   678   GST_OBJECT_UNLOCK (src);
       
   679 
       
   680   return res;
       
   681 }
       
   682 
       
   683 static gboolean
       
   684 gst_base_src_setcaps (GstPad * pad, GstCaps * caps)
       
   685 {
       
   686   GstBaseSrcClass *bclass;
       
   687   GstBaseSrc *bsrc;
       
   688   gboolean res = TRUE;
       
   689 
       
   690   bsrc = GST_BASE_SRC (GST_PAD_PARENT (pad));
       
   691   bclass = GST_BASE_SRC_GET_CLASS (bsrc);
       
   692 
       
   693   if (bclass->set_caps)
       
   694     res = bclass->set_caps (bsrc, caps);
       
   695 
       
   696   return res;
       
   697 }
       
   698 
       
   699 static GstCaps *
       
   700 gst_base_src_getcaps (GstPad * pad)
       
   701 {
       
   702   GstBaseSrcClass *bclass;
       
   703   GstBaseSrc *bsrc;
       
   704   GstCaps *caps = NULL;
       
   705 
       
   706   bsrc = GST_BASE_SRC (GST_PAD_PARENT (pad));
       
   707   bclass = GST_BASE_SRC_GET_CLASS (bsrc);
       
   708   if (bclass->get_caps)
       
   709     caps = bclass->get_caps (bsrc);
       
   710 
       
   711   if (caps == NULL) {
       
   712     GstPadTemplate *pad_template;
       
   713 
       
   714     pad_template =
       
   715         gst_element_class_get_pad_template (GST_ELEMENT_CLASS (bclass), "src");
       
   716     if (pad_template != NULL) {
       
   717       caps = gst_caps_ref (gst_pad_template_get_caps (pad_template));
       
   718     }
       
   719   }
       
   720   return caps;
       
   721 }
       
   722 
       
   723 static void
       
   724 gst_base_src_fixate (GstPad * pad, GstCaps * caps)
       
   725 {
       
   726   GstBaseSrcClass *bclass;
       
   727   GstBaseSrc *bsrc;
       
   728 
       
   729   bsrc = GST_BASE_SRC (gst_pad_get_parent (pad));
       
   730   bclass = GST_BASE_SRC_GET_CLASS (bsrc);
       
   731 
       
   732   if (bclass->fixate)
       
   733     bclass->fixate (bsrc, caps);
       
   734 
       
   735   gst_object_unref (bsrc);
       
   736 }
       
   737 
       
   738 static gboolean
       
   739 gst_base_src_default_query (GstBaseSrc * src, GstQuery * query)
       
   740 {
       
   741   gboolean res;
       
   742 
       
   743   switch (GST_QUERY_TYPE (query)) {
       
   744     case GST_QUERY_POSITION:
       
   745     {
       
   746       GstFormat format;
       
   747 
       
   748       gst_query_parse_position (query, &format, NULL);
       
   749       switch (format) {
       
   750         case GST_FORMAT_PERCENT:
       
   751         {
       
   752           gint64 percent;
       
   753           gint64 position;
       
   754           gint64 duration;
       
   755 
       
   756           position = src->segment.last_stop;
       
   757           duration = src->segment.duration;
       
   758 
       
   759           if (position != -1 && duration != -1) {
       
   760             if (position < duration)
       
   761               percent = gst_util_uint64_scale (GST_FORMAT_PERCENT_MAX, position,
       
   762                   duration);
       
   763             else
       
   764               percent = GST_FORMAT_PERCENT_MAX;
       
   765           } else
       
   766             percent = -1;
       
   767 
       
   768           gst_query_set_position (query, GST_FORMAT_PERCENT, percent);
       
   769           res = TRUE;
       
   770           break;
       
   771         }
       
   772         default:
       
   773         {
       
   774           gint64 position;
       
   775 
       
   776           position = src->segment.last_stop;
       
   777 
       
   778           if (position != -1) {
       
   779             /* convert to requested format */
       
   780             res =
       
   781                 gst_pad_query_convert (src->srcpad, src->segment.format,
       
   782                 position, &format, &position);
       
   783           } else
       
   784             res = TRUE;
       
   785 
       
   786           gst_query_set_position (query, format, position);
       
   787           break;
       
   788         }
       
   789       }
       
   790       break;
       
   791     }
       
   792     case GST_QUERY_DURATION:
       
   793     {
       
   794       GstFormat format;
       
   795 
       
   796       gst_query_parse_duration (query, &format, NULL);
       
   797 
       
   798       GST_DEBUG_OBJECT (src, "duration query in format %s",
       
   799           gst_format_get_name (format));
       
   800       switch (format) {
       
   801         case GST_FORMAT_PERCENT:
       
   802           gst_query_set_duration (query, GST_FORMAT_PERCENT,
       
   803               GST_FORMAT_PERCENT_MAX);
       
   804           res = TRUE;
       
   805           break;
       
   806         default:
       
   807         {
       
   808           gint64 duration;
       
   809 
       
   810           /* this is the duration as configured by the subclass. */
       
   811           duration = src->segment.duration;
       
   812 
       
   813           if (duration != -1) {
       
   814             /* convert to requested format, if this fails, we have a duration
       
   815              * but we cannot answer the query, we must return FALSE. */
       
   816             res =
       
   817                 gst_pad_query_convert (src->srcpad, src->segment.format,
       
   818                 duration, &format, &duration);
       
   819           } else {
       
   820             /* The subclass did not configure a duration, we assume that the
       
   821              * media has an unknown duration then and we return TRUE to report
       
   822              * this. Note that this is not the same as returning FALSE, which
       
   823              * means that we cannot report the duration at all. */
       
   824             res = TRUE;
       
   825           }
       
   826           gst_query_set_duration (query, format, duration);
       
   827           break;
       
   828         }
       
   829       }
       
   830       break;
       
   831     }
       
   832 
       
   833     case GST_QUERY_SEEKING:
       
   834     {
       
   835       gst_query_set_seeking (query, src->segment.format,
       
   836           src->seekable, 0, src->segment.duration);
       
   837       res = TRUE;
       
   838       break;
       
   839     }
       
   840     case GST_QUERY_SEGMENT:
       
   841     {
       
   842       gint64 start, stop;
       
   843 
       
   844       /* no end segment configured, current duration then */
       
   845       if ((stop = src->segment.stop) == -1)
       
   846         stop = src->segment.duration;
       
   847       start = src->segment.start;
       
   848 
       
   849       /* adjust to stream time */
       
   850       if (src->segment.time != -1) {
       
   851         start -= src->segment.time;
       
   852         if (stop != -1)
       
   853           stop -= src->segment.time;
       
   854       }
       
   855       gst_query_set_segment (query, src->segment.rate, src->segment.format,
       
   856           start, stop);
       
   857       res = TRUE;
       
   858       break;
       
   859     }
       
   860 
       
   861     case GST_QUERY_FORMATS:
       
   862     {
       
   863       gst_query_set_formats (query, 3, GST_FORMAT_DEFAULT,
       
   864           GST_FORMAT_BYTES, GST_FORMAT_PERCENT);
       
   865       res = TRUE;
       
   866       break;
       
   867     }
       
   868     case GST_QUERY_CONVERT:
       
   869     {
       
   870       GstFormat src_fmt, dest_fmt;
       
   871       gint64 src_val, dest_val;
       
   872 
       
   873       gst_query_parse_convert (query, &src_fmt, &src_val, &dest_fmt, &dest_val);
       
   874 
       
   875       /* we can only convert between equal formats... */
       
   876       if (src_fmt == dest_fmt) {
       
   877         dest_val = src_val;
       
   878         res = TRUE;
       
   879       } else
       
   880         res = FALSE;
       
   881 
       
   882       gst_query_set_convert (query, src_fmt, src_val, dest_fmt, dest_val);
       
   883       break;
       
   884     }
       
   885     case GST_QUERY_LATENCY:
       
   886     {
       
   887       GstClockTime min, max;
       
   888       gboolean live;
       
   889 
       
   890       /* Subclasses should override and implement something usefull */
       
   891       res = gst_base_src_query_latency (src, &live, &min, &max);
       
   892 
       
   893       GST_LOG_OBJECT (src, "report latency: live %d, min %" GST_TIME_FORMAT
       
   894           ", max %" GST_TIME_FORMAT, live, GST_TIME_ARGS (min),
       
   895           GST_TIME_ARGS (max));
       
   896 
       
   897       gst_query_set_latency (query, live, min, max);
       
   898       break;
       
   899     }
       
   900     case GST_QUERY_JITTER:
       
   901     case GST_QUERY_RATE:
       
   902     default:
       
   903       res = FALSE;
       
   904       break;
       
   905   }
       
   906   GST_DEBUG_OBJECT (src, "query %s returns %d", GST_QUERY_TYPE_NAME (query),
       
   907       res);
       
   908   return res;
       
   909 }
       
   910 
       
   911 static gboolean
       
   912 gst_base_src_query (GstPad * pad, GstQuery * query)
       
   913 {
       
   914   GstBaseSrc *src;
       
   915   GstBaseSrcClass *bclass;
       
   916   gboolean result = FALSE;
       
   917 
       
   918   src = GST_BASE_SRC (gst_pad_get_parent (pad));
       
   919 
       
   920   bclass = GST_BASE_SRC_GET_CLASS (src);
       
   921 
       
   922   if (bclass->query)
       
   923     result = bclass->query (src, query);
       
   924   else
       
   925     result = gst_pad_query_default (pad, query);
       
   926 
       
   927   gst_object_unref (src);
       
   928 
       
   929   return result;
       
   930 }
       
   931 
       
   932 static gboolean
       
   933 gst_base_src_default_do_seek (GstBaseSrc * src, GstSegment * segment)
       
   934 {
       
   935   gboolean res = TRUE;
       
   936 
       
   937   /* update our offset if the start/stop position was updated */
       
   938   if (segment->format == GST_FORMAT_BYTES) {
       
   939     segment->time = segment->start;
       
   940   } else if (segment->start == 0) {
       
   941     /* seek to start, we can implement a default for this. */
       
   942     segment->time = 0;
       
   943     res = TRUE;
       
   944   } else
       
   945     res = FALSE;
       
   946 
       
   947   return res;
       
   948 }
       
   949 
       
   950 static gboolean
       
   951 gst_base_src_do_seek (GstBaseSrc * src, GstSegment * segment)
       
   952 {
       
   953   GstBaseSrcClass *bclass;
       
   954   gboolean result = FALSE;
       
   955 
       
   956   bclass = GST_BASE_SRC_GET_CLASS (src);
       
   957 
       
   958   if (bclass->do_seek)
       
   959     result = bclass->do_seek (src, segment);
       
   960 
       
   961   return result;
       
   962 }
       
   963 
       
   964 #define SEEK_TYPE_IS_RELATIVE(t) (((t) != GST_SEEK_TYPE_NONE) && ((t) != GST_SEEK_TYPE_SET))
       
   965 
       
   966 static gboolean
       
   967 gst_base_src_default_prepare_seek_segment (GstBaseSrc * src, GstEvent * event,
       
   968     GstSegment * segment)
       
   969 {
       
   970   /* By default, we try one of 2 things:
       
   971    *   - For absolute seek positions, convert the requested position to our 
       
   972    *     configured processing format and place it in the output segment \
       
   973    *   - For relative seek positions, convert our current (input) values to the
       
   974    *     seek format, adjust by the relative seek offset and then convert back to
       
   975    *     the processing format
       
   976    */
       
   977   GstSeekType cur_type, stop_type;
       
   978   gint64 cur, stop;
       
   979   GstSeekFlags flags;
       
   980   GstFormat seek_format, dest_format;
       
   981   gdouble rate;
       
   982   gboolean update;
       
   983   gboolean res = TRUE;
       
   984 
       
   985   gst_event_parse_seek (event, &rate, &seek_format, &flags,
       
   986       &cur_type, &cur, &stop_type, &stop);
       
   987   dest_format = segment->format;
       
   988 
       
   989   if (seek_format == dest_format) {
       
   990     gst_segment_set_seek (segment, rate, seek_format, flags,
       
   991         cur_type, cur, stop_type, stop, &update);
       
   992     return TRUE;
       
   993   }
       
   994 
       
   995   if (cur_type != GST_SEEK_TYPE_NONE) {
       
   996     /* FIXME: Handle seek_cur & seek_end by converting the input segment vals */
       
   997     res =
       
   998         gst_pad_query_convert (src->srcpad, seek_format, cur, &dest_format,
       
   999         &cur);
       
  1000     cur_type = GST_SEEK_TYPE_SET;
       
  1001   }
       
  1002 
       
  1003   if (res && stop_type != GST_SEEK_TYPE_NONE) {
       
  1004     /* FIXME: Handle seek_cur & seek_end by converting the input segment vals */
       
  1005     res =
       
  1006         gst_pad_query_convert (src->srcpad, seek_format, stop, &dest_format,
       
  1007         &stop);
       
  1008     stop_type = GST_SEEK_TYPE_SET;
       
  1009   }
       
  1010 
       
  1011   /* And finally, configure our output segment in the desired format */
       
  1012   gst_segment_set_seek (segment, rate, dest_format, flags, cur_type, cur,
       
  1013       stop_type, stop, &update);
       
  1014 
       
  1015   if (!res)
       
  1016     goto no_format;
       
  1017 
       
  1018   return res;
       
  1019 
       
  1020 no_format:
       
  1021   {
       
  1022     GST_DEBUG_OBJECT (src, "undefined format given, seek aborted.");
       
  1023     return FALSE;
       
  1024   }
       
  1025 }
       
  1026 
       
  1027 static gboolean
       
  1028 gst_base_src_prepare_seek_segment (GstBaseSrc * src, GstEvent * event,
       
  1029     GstSegment * seeksegment)
       
  1030 {
       
  1031   GstBaseSrcClass *bclass;
       
  1032   gboolean result = FALSE;
       
  1033 
       
  1034   bclass = GST_BASE_SRC_GET_CLASS (src);
       
  1035 
       
  1036   if (bclass->prepare_seek_segment)
       
  1037     result = bclass->prepare_seek_segment (src, event, seeksegment);
       
  1038 
       
  1039   return result;
       
  1040 }
       
  1041 
       
  1042 /* this code implements the seeking. It is a good example
       
  1043  * handling all cases.
       
  1044  *
       
  1045  * A seek updates the currently configured segment.start
       
  1046  * and segment.stop values based on the SEEK_TYPE. If the
       
  1047  * segment.start value is updated, a seek to this new position
       
  1048  * should be performed.
       
  1049  *
       
  1050  * The seek can only be executed when we are not currently
       
  1051  * streaming any data, to make sure that this is the case, we
       
  1052  * acquire the STREAM_LOCK which is taken when we are in the
       
  1053  * _loop() function or when a getrange() is called. Normally
       
  1054  * we will not receive a seek if we are operating in pull mode
       
  1055  * though. When we operate as a live source we might block on the live
       
  1056  * cond, which does not release the STREAM_LOCK. Therefore we will try
       
  1057  * to grab the LIVE_LOCK instead of the STREAM_LOCK to make sure it is
       
  1058  * safe to perform the seek.
       
  1059  *
       
  1060  * When we are in the loop() function, we might be in the middle
       
  1061  * of pushing a buffer, which might block in a sink. To make sure
       
  1062  * that the push gets unblocked we push out a FLUSH_START event.
       
  1063  * Our loop function will get a WRONG_STATE return value from
       
  1064  * the push and will pause, effectively releasing the STREAM_LOCK.
       
  1065  *
       
  1066  * For a non-flushing seek, we pause the task, which might eventually
       
  1067  * release the STREAM_LOCK. We say eventually because when the sink
       
  1068  * blocks on the sample we might wait a very long time until the sink
       
  1069  * unblocks the sample. In any case we acquire the STREAM_LOCK and
       
  1070  * can continue the seek. A non-flushing seek is normally done in a 
       
  1071  * running pipeline to perform seamless playback, this means that the sink is
       
  1072  * PLAYING and will return from its chain function.
       
  1073  * In the case of a non-flushing seek we need to make sure that the
       
  1074  * data we output after the seek is continuous with the previous data,
       
  1075  * this is because a non-flushing seek does not reset the running-time
       
  1076  * to 0. We do this by closing the currently running segment, ie. sending
       
  1077  * a new_segment event with the stop position set to the last processed 
       
  1078  * position.
       
  1079  *
       
  1080  * After updating the segment.start/stop values, we prepare for
       
  1081  * streaming again. We push out a FLUSH_STOP to make the peer pad
       
  1082  * accept data again and we start our task again.
       
  1083  *
       
  1084  * A segment seek posts a message on the bus saying that the playback
       
  1085  * of the segment started. We store the segment flag internally because
       
  1086  * when we reach the segment.stop we have to post a segment.done
       
  1087  * instead of EOS when doing a segment seek.
       
  1088  */
       
  1089 /* FIXME (0.11), we have the unlock gboolean here because most current 
       
  1090  * implementations (fdsrc, -base/gst/tcp/, ...) unconditionally unlock, even when
       
  1091  * the streaming thread isn't running, resulting in bogus unlocks later when it 
       
  1092  * starts. This is fixed by adding unlock_stop, but we should still avoid unlocking
       
  1093  * unnecessarily for backwards compatibility. Ergo, the unlock variable stays
       
  1094  * until 0.11
       
  1095  */
       
  1096 static gboolean
       
  1097 gst_base_src_perform_seek (GstBaseSrc * src, GstEvent * event, gboolean unlock)
       
  1098 {
       
  1099   gboolean res = TRUE;
       
  1100   gdouble rate;
       
  1101   GstFormat seek_format, dest_format;
       
  1102   GstSeekFlags flags;
       
  1103   GstSeekType cur_type, stop_type;
       
  1104   gint64 cur, stop;
       
  1105   gboolean flush, playing;
       
  1106   gboolean update;
       
  1107   gboolean relative_seek = FALSE;
       
  1108   gboolean seekseg_configured = FALSE;
       
  1109   GstSegment seeksegment;
       
  1110 
       
  1111   GST_DEBUG_OBJECT (src, "doing seek");
       
  1112 
       
  1113   dest_format = src->segment.format;
       
  1114 
       
  1115   if (event) {
       
  1116     gst_event_parse_seek (event, &rate, &seek_format, &flags,
       
  1117         &cur_type, &cur, &stop_type, &stop);
       
  1118 
       
  1119     relative_seek = SEEK_TYPE_IS_RELATIVE (cur_type) ||
       
  1120         SEEK_TYPE_IS_RELATIVE (stop_type);
       
  1121 
       
  1122     if (dest_format != seek_format && !relative_seek) {
       
  1123       /* If we have an ABSOLUTE position (SEEK_SET only), we can convert it
       
  1124        * here before taking the stream lock, otherwise we must convert it later,
       
  1125        * once we have the stream lock and can read the current position */
       
  1126       gst_segment_init (&seeksegment, dest_format);
       
  1127 
       
  1128       if (!gst_base_src_prepare_seek_segment (src, event, &seeksegment))
       
  1129         goto prepare_failed;
       
  1130 
       
  1131       seekseg_configured = TRUE;
       
  1132     }
       
  1133 
       
  1134     flush = flags & GST_SEEK_FLAG_FLUSH;
       
  1135   } else {
       
  1136     flush = FALSE;
       
  1137   }
       
  1138 
       
  1139   /* send flush start */
       
  1140   if (flush)
       
  1141     gst_pad_push_event (src->srcpad, gst_event_new_flush_start ());
       
  1142   else
       
  1143     gst_pad_pause_task (src->srcpad);
       
  1144 
       
  1145   /* unblock streaming thread. */
       
  1146   gst_base_src_set_flushing (src, TRUE, FALSE, unlock, &playing);
       
  1147 
       
  1148   /* grab streaming lock, this should eventually be possible, either
       
  1149    * because the task is paused, our streaming thread stopped 
       
  1150    * or because our peer is flushing. */
       
  1151   GST_PAD_STREAM_LOCK (src->srcpad);
       
  1152 
       
  1153   gst_base_src_set_flushing (src, FALSE, playing, unlock, NULL);
       
  1154 
       
  1155   /* If we configured the seeksegment above, don't overwrite it now. Otherwise
       
  1156    * copy the current segment info into the temp segment that we can actually
       
  1157    * attempt the seek with. We only update the real segment if the seek suceeds. */
       
  1158   if (!seekseg_configured) {
       
  1159     memcpy (&seeksegment, &src->segment, sizeof (GstSegment));
       
  1160 
       
  1161     /* now configure the final seek segment */
       
  1162     if (event) {
       
  1163       if (src->segment.format != seek_format) {
       
  1164         /* OK, here's where we give the subclass a chance to convert the relative
       
  1165          * seek into an absolute one in the processing format. We set up any
       
  1166          * absolute seek above, before taking the stream lock. */
       
  1167         if (!gst_base_src_prepare_seek_segment (src, event, &seeksegment)) {
       
  1168           GST_DEBUG_OBJECT (src, "Preparing the seek failed after flushing. "
       
  1169               "Aborting seek");
       
  1170           res = FALSE;
       
  1171         }
       
  1172       } else {
       
  1173         /* The seek format matches our processing format, no need to ask the
       
  1174          * the subclass to configure the segment. */
       
  1175         gst_segment_set_seek (&seeksegment, rate, seek_format, flags,
       
  1176             cur_type, cur, stop_type, stop, &update);
       
  1177       }
       
  1178     }
       
  1179     /* Else, no seek event passed, so we're just (re)starting the 
       
  1180        current segment. */
       
  1181   }
       
  1182 
       
  1183   if (res) {
       
  1184     GST_DEBUG_OBJECT (src, "segment configured from %" G_GINT64_FORMAT
       
  1185         " to %" G_GINT64_FORMAT ", position %" G_GINT64_FORMAT,
       
  1186         seeksegment.start, seeksegment.stop, seeksegment.last_stop);
       
  1187 
       
  1188     /* do the seek, segment.last_stop contains the new position. */
       
  1189     res = gst_base_src_do_seek (src, &seeksegment);
       
  1190   }
       
  1191 
       
  1192   /* and prepare to continue streaming */
       
  1193   if (flush) {
       
  1194     /* send flush stop, peer will accept data and events again. We
       
  1195      * are not yet providing data as we still have the STREAM_LOCK. */
       
  1196     gst_pad_push_event (src->srcpad, gst_event_new_flush_stop ());
       
  1197   } else if (res && src->data.ABI.running) {
       
  1198     /* we are running the current segment and doing a non-flushing seek, 
       
  1199      * close the segment first based on the last_stop. */
       
  1200     GST_DEBUG_OBJECT (src, "closing running segment %" G_GINT64_FORMAT
       
  1201         " to %" G_GINT64_FORMAT, src->segment.start, src->segment.last_stop);
       
  1202 
       
  1203     /* queue the segment for sending in the stream thread */
       
  1204     if (src->priv->close_segment)
       
  1205       gst_event_unref (src->priv->close_segment);
       
  1206     src->priv->close_segment =
       
  1207         gst_event_new_new_segment_full (TRUE,
       
  1208         src->segment.rate, src->segment.applied_rate, src->segment.format,
       
  1209         src->segment.start, src->segment.last_stop, src->segment.time);
       
  1210   }
       
  1211 
       
  1212   /* The subclass must have converted the segment to the processing format 
       
  1213    * by now */
       
  1214   if (res && seeksegment.format != dest_format) {
       
  1215     GST_DEBUG_OBJECT (src, "Subclass failed to prepare a seek segment "
       
  1216         "in the correct format. Aborting seek.");
       
  1217     res = FALSE;
       
  1218   }
       
  1219 
       
  1220   /* if successfull seek, we update our real segment and push
       
  1221    * out the new segment. */
       
  1222   if (res) {
       
  1223     memcpy (&src->segment, &seeksegment, sizeof (GstSegment));
       
  1224 
       
  1225     if (src->segment.flags & GST_SEEK_FLAG_SEGMENT) {
       
  1226       gst_element_post_message (GST_ELEMENT (src),
       
  1227           gst_message_new_segment_start (GST_OBJECT (src),
       
  1228               src->segment.format, src->segment.last_stop));
       
  1229     }
       
  1230 
       
  1231     /* for deriving a stop position for the playback segment from the seek
       
  1232      * segment, we must take the duration when the stop is not set */
       
  1233     if ((stop = src->segment.stop) == -1)
       
  1234       stop = src->segment.duration;
       
  1235 
       
  1236     GST_DEBUG_OBJECT (src, "Sending newsegment from %" G_GINT64_FORMAT
       
  1237         " to %" G_GINT64_FORMAT, src->segment.start, stop);
       
  1238 
       
  1239     /* now replace the old segment so that we send it in the stream thread the
       
  1240      * next time it is scheduled. */
       
  1241     if (src->priv->start_segment)
       
  1242       gst_event_unref (src->priv->start_segment);
       
  1243     if (src->segment.rate >= 0.0) {
       
  1244       /* forward, we send data from last_stop to stop */
       
  1245       src->priv->start_segment =
       
  1246           gst_event_new_new_segment_full (FALSE,
       
  1247           src->segment.rate, src->segment.applied_rate, src->segment.format,
       
  1248           src->segment.last_stop, stop, src->segment.time);
       
  1249     } else {
       
  1250       /* reverse, we send data from stop to last_stop */
       
  1251       src->priv->start_segment =
       
  1252           gst_event_new_new_segment_full (FALSE,
       
  1253           src->segment.rate, src->segment.applied_rate, src->segment.format,
       
  1254           src->segment.start, src->segment.last_stop, src->segment.time);
       
  1255     }
       
  1256   }
       
  1257 
       
  1258   src->priv->discont = TRUE;
       
  1259   src->data.ABI.running = TRUE;
       
  1260   /* and restart the task in case it got paused explicitely or by
       
  1261    * the FLUSH_START event we pushed out. */
       
  1262   gst_pad_start_task (src->srcpad, (GstTaskFunction) gst_base_src_loop,
       
  1263       src->srcpad);
       
  1264 
       
  1265   /* and release the lock again so we can continue streaming */
       
  1266   GST_PAD_STREAM_UNLOCK (src->srcpad);
       
  1267 
       
  1268   return res;
       
  1269 
       
  1270   /* ERROR */
       
  1271 prepare_failed:
       
  1272   GST_DEBUG_OBJECT (src, "Preparing the seek failed before flushing. "
       
  1273       "Aborting seek");
       
  1274   return FALSE;
       
  1275 }
       
  1276 
       
  1277 static const GstQueryType *
       
  1278 gst_base_src_get_query_types (GstElement * element)
       
  1279 {
       
  1280   static const GstQueryType query_types[] = {
       
  1281     GST_QUERY_DURATION,
       
  1282     GST_QUERY_POSITION,
       
  1283     GST_QUERY_SEEKING,
       
  1284     GST_QUERY_SEGMENT,
       
  1285     GST_QUERY_FORMATS,
       
  1286     GST_QUERY_LATENCY,
       
  1287     GST_QUERY_JITTER,
       
  1288     GST_QUERY_RATE,
       
  1289     GST_QUERY_CONVERT,
       
  1290     0
       
  1291   };
       
  1292 
       
  1293   return query_types;
       
  1294 }
       
  1295 
       
  1296 /* all events send to this element directly. This is mainly done from the
       
  1297  * application.
       
  1298  */
       
  1299 static gboolean
       
  1300 gst_base_src_send_event (GstElement * element, GstEvent * event)
       
  1301 {
       
  1302   GstBaseSrc *src;
       
  1303   gboolean result = FALSE;
       
  1304 
       
  1305   src = GST_BASE_SRC (element);
       
  1306 
       
  1307   switch (GST_EVENT_TYPE (event)) {
       
  1308       /* bidirectional events */
       
  1309     case GST_EVENT_FLUSH_START:
       
  1310     case GST_EVENT_FLUSH_STOP:
       
  1311       /* sending random flushes downstream can break stuff,
       
  1312        * especially sync since all segment info will get flushed */
       
  1313       break;
       
  1314 
       
  1315       /* downstream serialized events */
       
  1316     case GST_EVENT_EOS:
       
  1317       /* queue EOS and make sure the task or pull function 
       
  1318        * performs the EOS actions. */
       
  1319       GST_LIVE_LOCK (src);
       
  1320       src->priv->pending_eos = TRUE;
       
  1321       GST_LIVE_UNLOCK (src);
       
  1322       result = TRUE;
       
  1323       break;
       
  1324     case GST_EVENT_NEWSEGMENT:
       
  1325       /* sending random NEWSEGMENT downstream can break sync. */
       
  1326       break;
       
  1327     case GST_EVENT_TAG:
       
  1328       /* sending tags could be useful, FIXME insert in dataflow */
       
  1329       break;
       
  1330     case GST_EVENT_BUFFERSIZE:
       
  1331       /* does not seem to make much sense currently */
       
  1332       break;
       
  1333 
       
  1334       /* upstream events */
       
  1335     case GST_EVENT_QOS:
       
  1336       /* elements should override send_event and do something */
       
  1337       break;
       
  1338     case GST_EVENT_SEEK:
       
  1339     {
       
  1340       gboolean started;
       
  1341 
       
  1342       GST_OBJECT_LOCK (src->srcpad);
       
  1343       if (GST_PAD_ACTIVATE_MODE (src->srcpad) == GST_ACTIVATE_PULL)
       
  1344         goto wrong_mode;
       
  1345       started = GST_PAD_ACTIVATE_MODE (src->srcpad) == GST_ACTIVATE_PUSH;
       
  1346       GST_OBJECT_UNLOCK (src->srcpad);
       
  1347 
       
  1348       if (started) {
       
  1349         /* when we are running in push mode, we can execute the
       
  1350          * seek right now, we need to unlock. */
       
  1351         result = gst_base_src_perform_seek (src, event, TRUE);
       
  1352       } else {
       
  1353         GstEvent **event_p;
       
  1354 
       
  1355         /* else we store the event and execute the seek when we
       
  1356          * get activated */
       
  1357         GST_OBJECT_LOCK (src);
       
  1358         event_p = &src->data.ABI.pending_seek;
       
  1359         gst_event_replace ((GstEvent **) event_p, event);
       
  1360         GST_OBJECT_UNLOCK (src);
       
  1361         /* assume the seek will work */
       
  1362         result = TRUE;
       
  1363       }
       
  1364       break;
       
  1365     }
       
  1366     case GST_EVENT_NAVIGATION:
       
  1367       /* could make sense for elements that do something with navigation events
       
  1368        * but then they would need to override the send_event function */
       
  1369       break;
       
  1370     case GST_EVENT_LATENCY:
       
  1371       /* does not seem to make sense currently */
       
  1372       break;
       
  1373 
       
  1374       /* custom events */
       
  1375     case GST_EVENT_CUSTOM_UPSTREAM:
       
  1376       /* override send_event if you want this */
       
  1377       break;
       
  1378     case GST_EVENT_CUSTOM_DOWNSTREAM:
       
  1379     case GST_EVENT_CUSTOM_BOTH:
       
  1380       /* FIXME, insert event in the dataflow */
       
  1381       break;
       
  1382     case GST_EVENT_CUSTOM_DOWNSTREAM_OOB:
       
  1383     case GST_EVENT_CUSTOM_BOTH_OOB:
       
  1384       /* insert a random custom event into the pipeline */
       
  1385       GST_DEBUG_OBJECT (src, "pushing custom OOB event downstream");
       
  1386       result = gst_pad_push_event (src->srcpad, event);
       
  1387       /* we gave away the ref to the event in the push */
       
  1388       event = NULL;
       
  1389       break;
       
  1390     default:
       
  1391       break;
       
  1392   }
       
  1393 done:
       
  1394   /* if we still have a ref to the event, unref it now */
       
  1395   if (event)
       
  1396     gst_event_unref (event);
       
  1397 
       
  1398   return result;
       
  1399 
       
  1400   /* ERRORS */
       
  1401 wrong_mode:
       
  1402   {
       
  1403     GST_DEBUG_OBJECT (src, "cannot perform seek when operating in pull mode");
       
  1404     GST_OBJECT_UNLOCK (src->srcpad);
       
  1405     result = FALSE;
       
  1406     goto done;
       
  1407   }
       
  1408 }
       
  1409 
       
  1410 static gboolean
       
  1411 gst_base_src_default_event (GstBaseSrc * src, GstEvent * event)
       
  1412 {
       
  1413   gboolean result;
       
  1414 
       
  1415   switch (GST_EVENT_TYPE (event)) {
       
  1416     case GST_EVENT_SEEK:
       
  1417       /* is normally called when in push mode */
       
  1418       if (!src->seekable)
       
  1419         goto not_seekable;
       
  1420 
       
  1421       result = gst_base_src_perform_seek (src, event, TRUE);
       
  1422       break;
       
  1423     case GST_EVENT_FLUSH_START:
       
  1424       /* cancel any blocking getrange, is normally called
       
  1425        * when in pull mode. */
       
  1426       result = gst_base_src_set_flushing (src, TRUE, FALSE, TRUE, NULL);
       
  1427       break;
       
  1428     case GST_EVENT_FLUSH_STOP:
       
  1429       result = gst_base_src_set_flushing (src, FALSE, TRUE, TRUE, NULL);
       
  1430       break;
       
  1431     default:
       
  1432       result = TRUE;
       
  1433       break;
       
  1434   }
       
  1435   return result;
       
  1436 
       
  1437   /* ERRORS */
       
  1438 not_seekable:
       
  1439   {
       
  1440     GST_DEBUG_OBJECT (src, "is not seekable");
       
  1441     return FALSE;
       
  1442   }
       
  1443 }
       
  1444 
       
  1445 static gboolean
       
  1446 gst_base_src_event_handler (GstPad * pad, GstEvent * event)
       
  1447 {
       
  1448   GstBaseSrc *src;
       
  1449   GstBaseSrcClass *bclass;
       
  1450   gboolean result = FALSE;
       
  1451 
       
  1452   src = GST_BASE_SRC (gst_pad_get_parent (pad));
       
  1453   bclass = GST_BASE_SRC_GET_CLASS (src);
       
  1454 
       
  1455   if (bclass->event) {
       
  1456     if (!(result = bclass->event (src, event)))
       
  1457       goto subclass_failed;
       
  1458   }
       
  1459 
       
  1460 done:
       
  1461   gst_event_unref (event);
       
  1462   gst_object_unref (src);
       
  1463 
       
  1464   return result;
       
  1465 
       
  1466   /* ERRORS */
       
  1467 subclass_failed:
       
  1468   {
       
  1469     GST_DEBUG_OBJECT (src, "subclass refused event");
       
  1470     goto done;
       
  1471   }
       
  1472 }
       
  1473 
       
  1474 static void
       
  1475 gst_base_src_set_property (GObject * object, guint prop_id,
       
  1476     const GValue * value, GParamSpec * pspec)
       
  1477 {
       
  1478   GstBaseSrc *src;
       
  1479 
       
  1480   src = GST_BASE_SRC (object);
       
  1481 
       
  1482   switch (prop_id) {
       
  1483     case PROP_BLOCKSIZE:
       
  1484       src->blocksize = g_value_get_ulong (value);
       
  1485       break;
       
  1486     case PROP_NUM_BUFFERS:
       
  1487       src->num_buffers = g_value_get_int (value);
       
  1488       break;
       
  1489     case PROP_TYPEFIND:
       
  1490       src->data.ABI.typefind = g_value_get_boolean (value);
       
  1491       break;
       
  1492     case PROP_DO_TIMESTAMP:
       
  1493       src->priv->do_timestamp = g_value_get_boolean (value);
       
  1494       break;
       
  1495     default:
       
  1496       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       
  1497       break;
       
  1498   }
       
  1499 }
       
  1500 
       
  1501 static void
       
  1502 gst_base_src_get_property (GObject * object, guint prop_id, GValue * value,
       
  1503     GParamSpec * pspec)
       
  1504 {
       
  1505   GstBaseSrc *src;
       
  1506 
       
  1507   src = GST_BASE_SRC (object);
       
  1508 
       
  1509   switch (prop_id) {
       
  1510     case PROP_BLOCKSIZE:
       
  1511       g_value_set_ulong (value, src->blocksize);
       
  1512       break;
       
  1513     case PROP_NUM_BUFFERS:
       
  1514       g_value_set_int (value, src->num_buffers);
       
  1515       break;
       
  1516     case PROP_TYPEFIND:
       
  1517       g_value_set_boolean (value, src->data.ABI.typefind);
       
  1518       break;
       
  1519     case PROP_DO_TIMESTAMP:
       
  1520       g_value_set_boolean (value, src->priv->do_timestamp);
       
  1521       break;
       
  1522     default:
       
  1523       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       
  1524       break;
       
  1525   }
       
  1526 }
       
  1527 
       
  1528 /* with STREAM_LOCK and LOCK */
       
  1529 static GstClockReturn
       
  1530 gst_base_src_wait (GstBaseSrc * basesrc, GstClock * clock, GstClockTime time)
       
  1531 {
       
  1532   GstClockReturn ret;
       
  1533   GstClockID id;
       
  1534 
       
  1535   id = gst_clock_new_single_shot_id (clock, time);
       
  1536 
       
  1537   basesrc->clock_id = id;
       
  1538   /* release the live lock while waiting */
       
  1539   GST_LIVE_UNLOCK (basesrc);
       
  1540 
       
  1541   ret = gst_clock_id_wait (id, NULL);
       
  1542 
       
  1543   GST_LIVE_LOCK (basesrc);
       
  1544   gst_clock_id_unref (id);
       
  1545   basesrc->clock_id = NULL;
       
  1546 
       
  1547   return ret;
       
  1548 }
       
  1549 
       
  1550 /* perform synchronisation on a buffer. 
       
  1551  * with STREAM_LOCK.
       
  1552  */
       
  1553 static GstClockReturn
       
  1554 gst_base_src_do_sync (GstBaseSrc * basesrc, GstBuffer * buffer)
       
  1555 {
       
  1556   GstClockReturn result;
       
  1557   GstClockTime start, end;
       
  1558   GstBaseSrcClass *bclass;
       
  1559   GstClockTime base_time;
       
  1560   GstClock *clock;
       
  1561   GstClockTime now = GST_CLOCK_TIME_NONE, timestamp;
       
  1562   gboolean do_timestamp, first, pseudo_live;
       
  1563 
       
  1564   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  1565 
       
  1566   start = end = -1;
       
  1567   if (bclass->get_times)
       
  1568     bclass->get_times (basesrc, buffer, &start, &end);
       
  1569 
       
  1570   /* get buffer timestamp */
       
  1571   timestamp = GST_BUFFER_TIMESTAMP (buffer);
       
  1572 
       
  1573   /* grab the lock to prepare for clocking and calculate the startup 
       
  1574    * latency. */
       
  1575   GST_OBJECT_LOCK (basesrc);
       
  1576 
       
  1577   /* if we are asked to sync against the clock we are a pseudo live element */
       
  1578   pseudo_live = (start != -1 && basesrc->is_live);
       
  1579   /* check for the first buffer */
       
  1580   first = (basesrc->priv->latency == -1);
       
  1581 
       
  1582   if (timestamp != -1 && pseudo_live) {
       
  1583     GstClockTime latency;
       
  1584 
       
  1585     /* we have a timestamp and a sync time, latency is the diff */
       
  1586     if (timestamp <= start)
       
  1587       latency = start - timestamp;
       
  1588     else
       
  1589       latency = 0;
       
  1590 
       
  1591     if (first) {
       
  1592       GST_DEBUG_OBJECT (basesrc, "pseudo_live with latency %" GST_TIME_FORMAT,
       
  1593           GST_TIME_ARGS (latency));
       
  1594       /* first time we calculate latency, just configure */
       
  1595       basesrc->priv->latency = latency;
       
  1596     } else {
       
  1597       if (basesrc->priv->latency != latency) {
       
  1598         /* we have a new latency, FIXME post latency message */
       
  1599         basesrc->priv->latency = latency;
       
  1600         GST_DEBUG_OBJECT (basesrc, "latency changed to %" GST_TIME_FORMAT,
       
  1601             GST_TIME_ARGS (latency));
       
  1602       }
       
  1603     }
       
  1604   } else if (first) {
       
  1605     GST_DEBUG_OBJECT (basesrc, "no latency needed, live %d, sync %d",
       
  1606         basesrc->is_live, start != -1);
       
  1607     basesrc->priv->latency = 0;
       
  1608   }
       
  1609 
       
  1610   /* get clock, if no clock, we can't sync or do timestamps */
       
  1611   if ((clock = GST_ELEMENT_CLOCK (basesrc)) == NULL)
       
  1612     goto no_clock;
       
  1613 
       
  1614   base_time = GST_ELEMENT_CAST (basesrc)->base_time;
       
  1615 
       
  1616   do_timestamp = basesrc->priv->do_timestamp;
       
  1617 
       
  1618   /* first buffer, calculate the timestamp offset */
       
  1619   if (first) {
       
  1620     GstClockTime running_time;
       
  1621 
       
  1622     now = gst_clock_get_time (clock);
       
  1623     running_time = now - base_time;
       
  1624 
       
  1625     GST_LOG_OBJECT (basesrc,
       
  1626         "startup timestamp: %" GST_TIME_FORMAT ", running_time %"
       
  1627         GST_TIME_FORMAT, GST_TIME_ARGS (timestamp),
       
  1628         GST_TIME_ARGS (running_time));
       
  1629 
       
  1630     if (pseudo_live && timestamp != -1) {
       
  1631       /* live source and we need to sync, add startup latency to all timestamps
       
  1632        * to get the real running_time. Live sources should always timestamp
       
  1633        * according to the current running time. */
       
  1634       basesrc->priv->ts_offset = GST_CLOCK_DIFF (timestamp, running_time);
       
  1635 
       
  1636       GST_LOG_OBJECT (basesrc, "live with sync, ts_offset %" GST_TIME_FORMAT,
       
  1637           GST_TIME_ARGS (basesrc->priv->ts_offset));
       
  1638     } else {
       
  1639       basesrc->priv->ts_offset = 0;
       
  1640       GST_LOG_OBJECT (basesrc, "no timestamp offset needed");
       
  1641     }
       
  1642 
       
  1643     if (!GST_CLOCK_TIME_IS_VALID (timestamp)) {
       
  1644       if (do_timestamp)
       
  1645         timestamp = running_time;
       
  1646       else
       
  1647         timestamp = 0;
       
  1648 
       
  1649       GST_BUFFER_TIMESTAMP (buffer) = timestamp;
       
  1650 
       
  1651       GST_LOG_OBJECT (basesrc, "created timestamp: %" GST_TIME_FORMAT,
       
  1652           GST_TIME_ARGS (timestamp));
       
  1653     }
       
  1654 
       
  1655     /* add the timestamp offset we need for sync */
       
  1656     timestamp += basesrc->priv->ts_offset;
       
  1657   } else {
       
  1658     /* not the first buffer, the timestamp is the diff between the clock and
       
  1659      * base_time */
       
  1660     if (do_timestamp && !GST_CLOCK_TIME_IS_VALID (timestamp)) {
       
  1661       now = gst_clock_get_time (clock);
       
  1662 
       
  1663       GST_BUFFER_TIMESTAMP (buffer) = now - base_time;
       
  1664 
       
  1665       GST_LOG_OBJECT (basesrc, "created timestamp: %" GST_TIME_FORMAT,
       
  1666           GST_TIME_ARGS (now - base_time));
       
  1667     }
       
  1668   }
       
  1669 
       
  1670   /* if we don't have a buffer timestamp, we don't sync */
       
  1671   if (!GST_CLOCK_TIME_IS_VALID (start))
       
  1672     goto no_sync;
       
  1673 
       
  1674   if (basesrc->is_live && GST_CLOCK_TIME_IS_VALID (timestamp)) {
       
  1675     /* for pseudo live sources, add our ts_offset to the timestamp */
       
  1676     GST_BUFFER_TIMESTAMP (buffer) += basesrc->priv->ts_offset;
       
  1677     start += basesrc->priv->ts_offset;
       
  1678   }
       
  1679 
       
  1680   GST_LOG_OBJECT (basesrc,
       
  1681       "waiting for clock, base time %" GST_TIME_FORMAT
       
  1682       ", stream_start %" GST_TIME_FORMAT,
       
  1683       GST_TIME_ARGS (base_time), GST_TIME_ARGS (start));
       
  1684   GST_OBJECT_UNLOCK (basesrc);
       
  1685 
       
  1686   result = gst_base_src_wait (basesrc, clock, start + base_time);
       
  1687 
       
  1688   GST_LOG_OBJECT (basesrc, "clock entry done: %d", result);
       
  1689 
       
  1690   return result;
       
  1691 
       
  1692   /* special cases */
       
  1693 no_clock:
       
  1694   {
       
  1695     GST_DEBUG_OBJECT (basesrc, "we have no clock");
       
  1696     GST_OBJECT_UNLOCK (basesrc);
       
  1697     return GST_CLOCK_OK;
       
  1698   }
       
  1699 no_sync:
       
  1700   {
       
  1701     GST_DEBUG_OBJECT (basesrc, "no sync needed");
       
  1702     GST_OBJECT_UNLOCK (basesrc);
       
  1703     return GST_CLOCK_OK;
       
  1704   }
       
  1705 }
       
  1706 
       
  1707 static gboolean
       
  1708 gst_base_src_update_length (GstBaseSrc * src, guint64 offset, guint * length)
       
  1709 {
       
  1710   guint64 size, maxsize;
       
  1711   GstBaseSrcClass *bclass;
       
  1712 
       
  1713   bclass = GST_BASE_SRC_GET_CLASS (src);
       
  1714 
       
  1715   /* only operate if we are working with bytes */
       
  1716   if (src->segment.format != GST_FORMAT_BYTES)
       
  1717     return TRUE;
       
  1718 
       
  1719   /* get total file size */
       
  1720   size = (guint64) src->segment.duration;
       
  1721 
       
  1722   /* the max amount of bytes to read is the total size or
       
  1723    * up to the segment.stop if present. */
       
  1724   if (src->segment.stop != -1)
       
  1725     maxsize = MIN (size, src->segment.stop);
       
  1726   else
       
  1727     maxsize = size;
       
  1728 
       
  1729   GST_DEBUG_OBJECT (src,
       
  1730       "reading offset %" G_GUINT64_FORMAT ", length %u, size %" G_GINT64_FORMAT
       
  1731       ", segment.stop %" G_GINT64_FORMAT ", maxsize %" G_GINT64_FORMAT, offset,
       
  1732       *length, size, src->segment.stop, maxsize);
       
  1733 
       
  1734   /* check size if we have one */
       
  1735   if (maxsize != -1) {
       
  1736     /* if we run past the end, check if the file became bigger and 
       
  1737      * retry. */
       
  1738     if (G_UNLIKELY (offset + *length >= maxsize)) {
       
  1739       /* see if length of the file changed */
       
  1740       if (bclass->get_size)
       
  1741         if (!bclass->get_size (src, &size))
       
  1742           size = -1;
       
  1743 
       
  1744       gst_segment_set_duration (&src->segment, GST_FORMAT_BYTES, size);
       
  1745 
       
  1746       /* make sure we don't exceed the configured segment stop
       
  1747        * if it was set */
       
  1748       if (src->segment.stop != -1)
       
  1749         maxsize = MIN (size, src->segment.stop);
       
  1750       else
       
  1751         maxsize = size;
       
  1752 
       
  1753       /* if we are at or past the end, EOS */
       
  1754       if (G_UNLIKELY (offset >= maxsize))
       
  1755         goto unexpected_length;
       
  1756 
       
  1757       /* else we can clip to the end */
       
  1758       if (G_UNLIKELY (offset + *length >= maxsize))
       
  1759         *length = maxsize - offset;
       
  1760 
       
  1761     }
       
  1762   }
       
  1763 
       
  1764   /* keep track of current position. segment is in bytes, we checked 
       
  1765    * that above. */
       
  1766   gst_segment_set_last_stop (&src->segment, GST_FORMAT_BYTES, offset);
       
  1767 
       
  1768   return TRUE;
       
  1769 
       
  1770   /* ERRORS */
       
  1771 unexpected_length:
       
  1772   {
       
  1773     return FALSE;
       
  1774   }
       
  1775 }
       
  1776 
       
  1777 /* must be called with LIVE_LOCK */
       
  1778 static GstFlowReturn
       
  1779 gst_base_src_get_range (GstBaseSrc * src, guint64 offset, guint length,
       
  1780     GstBuffer ** buf)
       
  1781 {
       
  1782   GstFlowReturn ret;
       
  1783   GstBaseSrcClass *bclass;
       
  1784   GstClockReturn status;
       
  1785 
       
  1786   bclass = GST_BASE_SRC_GET_CLASS (src);
       
  1787 
       
  1788   if (src->is_live) {
       
  1789     while (G_UNLIKELY (!src->live_running)) {
       
  1790       ret = gst_base_src_wait_playing (src);
       
  1791       if (ret != GST_FLOW_OK)
       
  1792         goto stopped;
       
  1793     }
       
  1794   }
       
  1795 
       
  1796   if (G_UNLIKELY (!GST_OBJECT_FLAG_IS_SET (src, GST_BASE_SRC_STARTED)))
       
  1797     goto not_started;
       
  1798 
       
  1799   if (G_UNLIKELY (!bclass->create))
       
  1800     goto no_function;
       
  1801 
       
  1802   if (G_UNLIKELY (!gst_base_src_update_length (src, offset, &length)))
       
  1803     goto unexpected_length;
       
  1804 
       
  1805   /* normally we don't count buffers */
       
  1806   if (G_UNLIKELY (src->num_buffers_left >= 0)) {
       
  1807     if (src->num_buffers_left == 0)
       
  1808       goto reached_num_buffers;
       
  1809     else
       
  1810       src->num_buffers_left--;
       
  1811   }
       
  1812 
       
  1813   GST_DEBUG_OBJECT (src,
       
  1814       "calling create offset %" G_GUINT64_FORMAT " length %u, time %"
       
  1815       G_GINT64_FORMAT, offset, length, src->segment.time);
       
  1816 
       
  1817   ret = bclass->create (src, offset, length, buf);
       
  1818   if (G_UNLIKELY (ret != GST_FLOW_OK))
       
  1819     goto not_ok;
       
  1820 
       
  1821   /* no timestamp set and we are at offset 0, we can timestamp with 0 */
       
  1822   if (offset == 0 && src->segment.time == 0
       
  1823       && GST_BUFFER_TIMESTAMP (*buf) == -1)
       
  1824     GST_BUFFER_TIMESTAMP (*buf) = 0;
       
  1825 
       
  1826   /* now sync before pushing the buffer */
       
  1827   status = gst_base_src_do_sync (src, *buf);
       
  1828 
       
  1829   /* waiting for the clock could have made us flushing */
       
  1830   if (G_UNLIKELY (src->priv->flushing))
       
  1831     goto flushing;
       
  1832 
       
  1833   if (G_UNLIKELY (src->priv->pending_eos))
       
  1834     goto eos;
       
  1835 
       
  1836   switch (status) {
       
  1837     case GST_CLOCK_EARLY:
       
  1838       /* the buffer is too late. We currently don't drop the buffer. */
       
  1839       GST_DEBUG_OBJECT (src, "buffer too late!, returning anyway");
       
  1840       break;
       
  1841     case GST_CLOCK_OK:
       
  1842       /* buffer synchronised properly */
       
  1843       GST_DEBUG_OBJECT (src, "buffer ok");
       
  1844       break;
       
  1845     case GST_CLOCK_UNSCHEDULED:
       
  1846       /* this case is triggered when we were waiting for the clock and
       
  1847        * it got unlocked because we did a state change. We return 
       
  1848        * WRONG_STATE in this case to stop the dataflow also get rid of the
       
  1849        * produced buffer. */
       
  1850       GST_DEBUG_OBJECT (src,
       
  1851           "clock was unscheduled (%d), returning WRONG_STATE", status);
       
  1852       gst_buffer_unref (*buf);
       
  1853       *buf = NULL;
       
  1854       ret = GST_FLOW_WRONG_STATE;
       
  1855       break;
       
  1856     default:
       
  1857       /* all other result values are unexpected and errors */
       
  1858       GST_ELEMENT_ERROR (src, CORE, CLOCK,
       
  1859           (_("Internal clock error.")),
       
  1860           ("clock returned unexpected return value %d", status));
       
  1861       gst_buffer_unref (*buf);
       
  1862       *buf = NULL;
       
  1863       ret = GST_FLOW_ERROR;
       
  1864       break;
       
  1865   }
       
  1866   return ret;
       
  1867 
       
  1868   /* ERROR */
       
  1869 stopped:
       
  1870   {
       
  1871     GST_DEBUG_OBJECT (src, "wait_playing returned %d (%s)", ret,
       
  1872         gst_flow_get_name (ret));
       
  1873     return ret;
       
  1874   }
       
  1875 not_ok:
       
  1876   {
       
  1877     GST_DEBUG_OBJECT (src, "create returned %d (%s)", ret,
       
  1878         gst_flow_get_name (ret));
       
  1879     return ret;
       
  1880   }
       
  1881 not_started:
       
  1882   {
       
  1883     GST_DEBUG_OBJECT (src, "getrange but not started");
       
  1884     return GST_FLOW_WRONG_STATE;
       
  1885   }
       
  1886 no_function:
       
  1887   {
       
  1888     GST_DEBUG_OBJECT (src, "no create function");
       
  1889     return GST_FLOW_ERROR;
       
  1890   }
       
  1891 unexpected_length:
       
  1892   {
       
  1893     GST_DEBUG_OBJECT (src, "unexpected length %u (offset=%" G_GUINT64_FORMAT
       
  1894         ", size=%" G_GINT64_FORMAT ")", length, offset, src->segment.duration);
       
  1895     return GST_FLOW_UNEXPECTED;
       
  1896   }
       
  1897 reached_num_buffers:
       
  1898   {
       
  1899     GST_DEBUG_OBJECT (src, "sent all buffers");
       
  1900     return GST_FLOW_UNEXPECTED;
       
  1901   }
       
  1902 flushing:
       
  1903   {
       
  1904     GST_DEBUG_OBJECT (src, "we are flushing");
       
  1905     gst_buffer_unref (*buf);
       
  1906     *buf = NULL;
       
  1907     return GST_FLOW_WRONG_STATE;
       
  1908   }
       
  1909 eos:
       
  1910   {
       
  1911     GST_DEBUG_OBJECT (src, "we are EOS");
       
  1912     gst_buffer_unref (*buf);
       
  1913     *buf = NULL;
       
  1914     return GST_FLOW_UNEXPECTED;
       
  1915   }
       
  1916 }
       
  1917 
       
  1918 static GstFlowReturn
       
  1919 gst_base_src_pad_get_range (GstPad * pad, guint64 offset, guint length,
       
  1920     GstBuffer ** buf)
       
  1921 {
       
  1922   GstBaseSrc *src;
       
  1923   GstFlowReturn res;
       
  1924 
       
  1925   src = GST_BASE_SRC (gst_pad_get_parent (pad));
       
  1926 
       
  1927   GST_LIVE_LOCK (src);
       
  1928   if (G_UNLIKELY (src->priv->flushing))
       
  1929     goto flushing;
       
  1930 
       
  1931   /* if we're EOS, return right away */
       
  1932   if (G_UNLIKELY (src->priv->pending_eos))
       
  1933     goto eos;
       
  1934 
       
  1935   res = gst_base_src_get_range (src, offset, length, buf);
       
  1936 
       
  1937 done:
       
  1938   GST_LIVE_UNLOCK (src);
       
  1939 
       
  1940   gst_object_unref (src);
       
  1941 
       
  1942   return res;
       
  1943 
       
  1944   /* ERRORS */
       
  1945 flushing:
       
  1946   {
       
  1947     GST_DEBUG_OBJECT (src, "we are flushing");
       
  1948     res = GST_FLOW_WRONG_STATE;
       
  1949     goto done;
       
  1950   }
       
  1951 eos:
       
  1952   {
       
  1953     GST_DEBUG_OBJECT (src, "we are EOS");
       
  1954     res = GST_FLOW_UNEXPECTED;
       
  1955     goto done;
       
  1956   }
       
  1957 }
       
  1958 
       
  1959 static gboolean
       
  1960 gst_base_src_default_check_get_range (GstBaseSrc * src)
       
  1961 {
       
  1962   gboolean res;
       
  1963 
       
  1964   if (!GST_OBJECT_FLAG_IS_SET (src, GST_BASE_SRC_STARTED)) {
       
  1965     GST_LOG_OBJECT (src, "doing start/stop to check get_range support");
       
  1966     if (G_LIKELY (gst_base_src_start (src)))
       
  1967       gst_base_src_stop (src);
       
  1968   }
       
  1969 
       
  1970   /* we can operate in getrange mode if the native format is bytes
       
  1971    * and we are seekable, this condition is set in the random_access
       
  1972    * flag and is set in the _start() method. */
       
  1973   res = src->random_access;
       
  1974 
       
  1975   return res;
       
  1976 }
       
  1977 
       
  1978 static gboolean
       
  1979 gst_base_src_check_get_range (GstBaseSrc * src)
       
  1980 {
       
  1981   GstBaseSrcClass *bclass;
       
  1982   gboolean res;
       
  1983 
       
  1984   bclass = GST_BASE_SRC_GET_CLASS (src);
       
  1985 
       
  1986   if (bclass->check_get_range == NULL)
       
  1987     goto no_function;
       
  1988 
       
  1989   res = bclass->check_get_range (src);
       
  1990   GST_LOG_OBJECT (src, "%s() returned %d",
       
  1991       GST_DEBUG_FUNCPTR_NAME (bclass->check_get_range), (gint) res);
       
  1992 
       
  1993   return res;
       
  1994 
       
  1995   /* ERRORS */
       
  1996 no_function:
       
  1997   {
       
  1998     GST_WARNING_OBJECT (src, "no check_get_range function set");
       
  1999     return FALSE;
       
  2000   }
       
  2001 }
       
  2002 
       
  2003 static gboolean
       
  2004 gst_base_src_pad_check_get_range (GstPad * pad)
       
  2005 {
       
  2006   GstBaseSrc *src;
       
  2007   gboolean res;
       
  2008 
       
  2009   src = GST_BASE_SRC (GST_OBJECT_PARENT (pad));
       
  2010 
       
  2011   res = gst_base_src_check_get_range (src);
       
  2012 
       
  2013   return res;
       
  2014 }
       
  2015 
       
  2016 static void
       
  2017 gst_base_src_loop (GstPad * pad)
       
  2018 {
       
  2019   GstBaseSrc *src;
       
  2020   GstBuffer *buf = NULL;
       
  2021   GstFlowReturn ret;
       
  2022   gint64 position;
       
  2023   gboolean eos;
       
  2024   gulong blocksize;
       
  2025 
       
  2026   eos = FALSE;
       
  2027 
       
  2028   src = GST_BASE_SRC (GST_OBJECT_PARENT (pad));
       
  2029 
       
  2030   GST_LIVE_LOCK (src);
       
  2031   if (G_UNLIKELY (src->priv->flushing))
       
  2032     goto flushing;
       
  2033 
       
  2034   /* if we're EOS, return right away */
       
  2035   if (G_UNLIKELY (src->priv->pending_eos))
       
  2036     goto eos;
       
  2037 
       
  2038   src->priv->last_sent_eos = FALSE;
       
  2039 
       
  2040   blocksize = src->blocksize;
       
  2041 
       
  2042   /* if we operate in bytes, we can calculate an offset */
       
  2043   if (src->segment.format == GST_FORMAT_BYTES) {
       
  2044     position = src->segment.last_stop;
       
  2045     /* for negative rates, start with subtracting the blocksize */
       
  2046     if (src->segment.rate < 0.0) {
       
  2047       /* we cannot go below segment.start */
       
  2048       if (position > src->segment.start + blocksize)
       
  2049         position -= blocksize;
       
  2050       else {
       
  2051         /* last block, remainder up to segment.start */
       
  2052         blocksize = position - src->segment.start;
       
  2053         position = src->segment.start;
       
  2054       }
       
  2055     }
       
  2056   } else
       
  2057     position = -1;
       
  2058 
       
  2059   ret = gst_base_src_get_range (src, position, blocksize, &buf);
       
  2060   if (G_UNLIKELY (ret != GST_FLOW_OK)) {
       
  2061     GST_INFO_OBJECT (src, "pausing after gst_base_src_get_range() = %s",
       
  2062         gst_flow_get_name (ret));
       
  2063     GST_LIVE_UNLOCK (src);
       
  2064     goto pause;
       
  2065   }
       
  2066   /* this should not happen */
       
  2067   if (G_UNLIKELY (buf == NULL))
       
  2068     goto null_buffer;
       
  2069 
       
  2070   /* push events to close/start our segment before we push the buffer. */
       
  2071   if (G_UNLIKELY (src->priv->close_segment)) {
       
  2072     gst_pad_push_event (pad, src->priv->close_segment);
       
  2073     src->priv->close_segment = NULL;
       
  2074   }
       
  2075   if (G_UNLIKELY (src->priv->start_segment)) {
       
  2076     gst_pad_push_event (pad, src->priv->start_segment);
       
  2077     src->priv->start_segment = NULL;
       
  2078   }
       
  2079 
       
  2080   /* figure out the new position */
       
  2081   switch (src->segment.format) {
       
  2082     case GST_FORMAT_BYTES:
       
  2083     {
       
  2084       guint bufsize = GST_BUFFER_SIZE (buf);
       
  2085 
       
  2086       /* we subtracted above for negative rates */
       
  2087       if (src->segment.rate >= 0.0)
       
  2088         position += bufsize;
       
  2089       break;
       
  2090     }
       
  2091     case GST_FORMAT_TIME:
       
  2092     {
       
  2093       GstClockTime start, duration;
       
  2094 
       
  2095       start = GST_BUFFER_TIMESTAMP (buf);
       
  2096       duration = GST_BUFFER_DURATION (buf);
       
  2097 
       
  2098       if (GST_CLOCK_TIME_IS_VALID (start))
       
  2099         position = start;
       
  2100       else
       
  2101         position = src->segment.last_stop;
       
  2102 
       
  2103       if (GST_CLOCK_TIME_IS_VALID (duration)) {
       
  2104         if (src->segment.rate >= 0.0)
       
  2105           position += duration;
       
  2106         else if (position > duration)
       
  2107           position -= duration;
       
  2108         else
       
  2109           position = 0;
       
  2110       }
       
  2111       break;
       
  2112     }
       
  2113     case GST_FORMAT_DEFAULT:
       
  2114       if (src->segment.rate >= 0.0)
       
  2115         position = GST_BUFFER_OFFSET_END (buf);
       
  2116       else
       
  2117         position = GST_BUFFER_OFFSET (buf);
       
  2118       break;
       
  2119     default:
       
  2120       position = -1;
       
  2121       break;
       
  2122   }
       
  2123   if (position != -1) {
       
  2124     if (src->segment.rate >= 0.0) {
       
  2125       /* positive rate, check if we reached the stop */
       
  2126       if (src->segment.stop != -1) {
       
  2127         if (position >= src->segment.stop) {
       
  2128           eos = TRUE;
       
  2129           position = src->segment.stop;
       
  2130         }
       
  2131       }
       
  2132     } else {
       
  2133       /* negative rate, check if we reached the start. start is always set to
       
  2134        * something different from -1 */
       
  2135       if (position <= src->segment.start) {
       
  2136         eos = TRUE;
       
  2137         position = src->segment.start;
       
  2138       }
       
  2139       /* when going reverse, all buffers are DISCONT */
       
  2140       src->priv->discont = TRUE;
       
  2141     }
       
  2142     gst_segment_set_last_stop (&src->segment, src->segment.format, position);
       
  2143   }
       
  2144 
       
  2145   if (G_UNLIKELY (src->priv->discont)) {
       
  2146     buf = gst_buffer_make_metadata_writable (buf);
       
  2147     GST_BUFFER_FLAG_SET (buf, GST_BUFFER_FLAG_DISCONT);
       
  2148     src->priv->discont = FALSE;
       
  2149   }
       
  2150   GST_LIVE_UNLOCK (src);
       
  2151 
       
  2152   ret = gst_pad_push (pad, buf);
       
  2153   if (G_UNLIKELY (ret != GST_FLOW_OK)) {
       
  2154     GST_INFO_OBJECT (src, "pausing after gst_pad_push() = %s",
       
  2155         gst_flow_get_name (ret));
       
  2156     goto pause;
       
  2157   }
       
  2158 
       
  2159   if (G_UNLIKELY (eos)) {
       
  2160     GST_INFO_OBJECT (src, "pausing after end of segment");
       
  2161     ret = GST_FLOW_UNEXPECTED;
       
  2162     goto pause;
       
  2163   }
       
  2164 
       
  2165 done:
       
  2166   return;
       
  2167 
       
  2168   /* special cases */
       
  2169 flushing:
       
  2170   {
       
  2171     GST_DEBUG_OBJECT (src, "we are flushing");
       
  2172     GST_LIVE_UNLOCK (src);
       
  2173     ret = GST_FLOW_WRONG_STATE;
       
  2174     goto pause;
       
  2175   }
       
  2176 eos:
       
  2177   {
       
  2178     GST_DEBUG_OBJECT (src, "we are EOS");
       
  2179     GST_LIVE_UNLOCK (src);
       
  2180     ret = GST_FLOW_UNEXPECTED;
       
  2181     goto pause;
       
  2182   }
       
  2183 pause:
       
  2184   {
       
  2185     const gchar *reason = gst_flow_get_name (ret);
       
  2186 
       
  2187     GST_DEBUG_OBJECT (src, "pausing task, reason %s", reason);
       
  2188     src->data.ABI.running = FALSE;
       
  2189     gst_pad_pause_task (pad);
       
  2190     if (GST_FLOW_IS_FATAL (ret) || ret == GST_FLOW_NOT_LINKED) {
       
  2191       if (ret == GST_FLOW_UNEXPECTED) {
       
  2192         /* perform EOS logic */
       
  2193         if (src->segment.flags & GST_SEEK_FLAG_SEGMENT) {
       
  2194           gst_element_post_message (GST_ELEMENT_CAST (src),
       
  2195               gst_message_new_segment_done (GST_OBJECT_CAST (src),
       
  2196                   src->segment.format, src->segment.last_stop));
       
  2197         } else {
       
  2198           gst_pad_push_event (pad, gst_event_new_eos ());
       
  2199           src->priv->last_sent_eos = TRUE;
       
  2200         }
       
  2201       } else {
       
  2202         /* for fatal errors we post an error message, post the error
       
  2203          * first so the app knows about the error first. */
       
  2204         GST_ELEMENT_ERROR (src, STREAM, FAILED,
       
  2205             (_("Internal data flow error.")),
       
  2206             ("streaming task paused, reason %s (%d)", reason, ret));
       
  2207         gst_pad_push_event (pad, gst_event_new_eos ());
       
  2208         src->priv->last_sent_eos = TRUE;
       
  2209       }
       
  2210     }
       
  2211     goto done;
       
  2212   }
       
  2213 null_buffer:
       
  2214   {
       
  2215     GST_ELEMENT_ERROR (src, STREAM, FAILED,
       
  2216         (_("Internal data flow error.")), ("element returned NULL buffer"));
       
  2217     GST_LIVE_UNLOCK (src);
       
  2218     /* we finished the segment on error */
       
  2219     ret = GST_FLOW_ERROR;
       
  2220     goto done;
       
  2221   }
       
  2222 }
       
  2223 
       
  2224 /* default negotiation code. 
       
  2225  *
       
  2226  * Take intersection between src and sink pads, take first
       
  2227  * caps and fixate. 
       
  2228  */
       
  2229 static gboolean
       
  2230 gst_base_src_default_negotiate (GstBaseSrc * basesrc)
       
  2231 {
       
  2232   GstCaps *thiscaps;
       
  2233   GstCaps *caps = NULL;
       
  2234   GstCaps *peercaps = NULL;
       
  2235   gboolean result = FALSE;
       
  2236 
       
  2237   /* first see what is possible on our source pad */
       
  2238   thiscaps = gst_pad_get_caps (GST_BASE_SRC_PAD (basesrc));
       
  2239   GST_DEBUG_OBJECT (basesrc, "caps of src: %" GST_PTR_FORMAT, thiscaps);
       
  2240   /* nothing or anything is allowed, we're done */
       
  2241   if (thiscaps == NULL || gst_caps_is_any (thiscaps))
       
  2242     goto no_nego_needed;
       
  2243 
       
  2244   /* get the peer caps */
       
  2245   peercaps = gst_pad_peer_get_caps (GST_BASE_SRC_PAD (basesrc));
       
  2246   GST_DEBUG_OBJECT (basesrc, "caps of peer: %" GST_PTR_FORMAT, peercaps);
       
  2247   if (peercaps) {
       
  2248     GstCaps *icaps;
       
  2249 
       
  2250     /* get intersection */
       
  2251     icaps = gst_caps_intersect (thiscaps, peercaps);
       
  2252     GST_DEBUG_OBJECT (basesrc, "intersect: %" GST_PTR_FORMAT, icaps);
       
  2253     gst_caps_unref (thiscaps);
       
  2254     gst_caps_unref (peercaps);
       
  2255     if (icaps) {
       
  2256       /* take first (and best, since they are sorted) possibility */
       
  2257       caps = gst_caps_copy_nth (icaps, 0);
       
  2258       gst_caps_unref (icaps);
       
  2259     }
       
  2260   } else {
       
  2261     /* no peer, work with our own caps then */
       
  2262     caps = thiscaps;
       
  2263   }
       
  2264   if (caps) {
       
  2265     caps = gst_caps_make_writable (caps);
       
  2266     gst_caps_truncate (caps);
       
  2267 
       
  2268     /* now fixate */
       
  2269     if (!gst_caps_is_empty (caps)) {
       
  2270       gst_pad_fixate_caps (GST_BASE_SRC_PAD (basesrc), caps);
       
  2271       GST_DEBUG_OBJECT (basesrc, "fixated to: %" GST_PTR_FORMAT, caps);
       
  2272 
       
  2273       if (gst_caps_is_any (caps)) {
       
  2274         /* hmm, still anything, so element can do anything and
       
  2275          * nego is not needed */
       
  2276         result = TRUE;
       
  2277       } else if (gst_caps_is_fixed (caps)) {
       
  2278         /* yay, fixed caps, use those then */
       
  2279         gst_pad_set_caps (GST_BASE_SRC_PAD (basesrc), caps);
       
  2280         result = TRUE;
       
  2281       }
       
  2282     }
       
  2283     gst_caps_unref (caps);
       
  2284   }
       
  2285   return result;
       
  2286 
       
  2287 no_nego_needed:
       
  2288   {
       
  2289     GST_DEBUG_OBJECT (basesrc, "no negotiation needed");
       
  2290     if (thiscaps)
       
  2291       gst_caps_unref (thiscaps);
       
  2292     return TRUE;
       
  2293   }
       
  2294 }
       
  2295 
       
  2296 static gboolean
       
  2297 gst_base_src_negotiate (GstBaseSrc * basesrc)
       
  2298 {
       
  2299   GstBaseSrcClass *bclass;
       
  2300   gboolean result = TRUE;
       
  2301 
       
  2302   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  2303 
       
  2304   if (bclass->negotiate)
       
  2305     result = bclass->negotiate (basesrc);
       
  2306 
       
  2307   return result;
       
  2308 }
       
  2309 
       
  2310 static gboolean
       
  2311 gst_base_src_start (GstBaseSrc * basesrc)
       
  2312 {
       
  2313   GstBaseSrcClass *bclass;
       
  2314   gboolean result;
       
  2315   guint64 size;
       
  2316 
       
  2317   if (GST_OBJECT_FLAG_IS_SET (basesrc, GST_BASE_SRC_STARTED))
       
  2318     return TRUE;
       
  2319 
       
  2320   GST_DEBUG_OBJECT (basesrc, "starting source");
       
  2321 
       
  2322   basesrc->num_buffers_left = basesrc->num_buffers;
       
  2323 
       
  2324   gst_segment_init (&basesrc->segment, basesrc->segment.format);
       
  2325   basesrc->data.ABI.running = FALSE;
       
  2326 
       
  2327   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  2328   if (bclass->start)
       
  2329     result = bclass->start (basesrc);
       
  2330   else
       
  2331     result = TRUE;
       
  2332 
       
  2333   if (!result)
       
  2334     goto could_not_start;
       
  2335 
       
  2336   GST_OBJECT_FLAG_SET (basesrc, GST_BASE_SRC_STARTED);
       
  2337 
       
  2338   /* figure out the size */
       
  2339   if (basesrc->segment.format == GST_FORMAT_BYTES) {
       
  2340     if (bclass->get_size) {
       
  2341       if (!(result = bclass->get_size (basesrc, &size)))
       
  2342         size = -1;
       
  2343     } else {
       
  2344       result = FALSE;
       
  2345       size = -1;
       
  2346     }
       
  2347     GST_DEBUG_OBJECT (basesrc, "setting size %" G_GUINT64_FORMAT, size);
       
  2348     /* only update the size when operating in bytes, subclass is supposed
       
  2349      * to set duration in the start method for other formats */
       
  2350     gst_segment_set_duration (&basesrc->segment, GST_FORMAT_BYTES, size);
       
  2351   } else {
       
  2352     size = -1;
       
  2353   }
       
  2354 
       
  2355   GST_DEBUG_OBJECT (basesrc,
       
  2356       "format: %d, have size: %d, size: %" G_GUINT64_FORMAT ", duration: %"
       
  2357       G_GINT64_FORMAT, basesrc->segment.format, result, size,
       
  2358       basesrc->segment.duration);
       
  2359 
       
  2360   /* check if we can seek */
       
  2361   if (bclass->is_seekable)
       
  2362     basesrc->seekable = bclass->is_seekable (basesrc);
       
  2363   else
       
  2364     basesrc->seekable = FALSE;
       
  2365 
       
  2366   GST_DEBUG_OBJECT (basesrc, "is seekable: %d", basesrc->seekable);
       
  2367 
       
  2368   /* update for random access flag */
       
  2369   basesrc->random_access = basesrc->seekable &&
       
  2370       basesrc->segment.format == GST_FORMAT_BYTES;
       
  2371 
       
  2372   GST_DEBUG_OBJECT (basesrc, "is random_access: %d", basesrc->random_access);
       
  2373 
       
  2374   /* run typefind if we are random_access and the typefinding is enabled. */
       
  2375   if (basesrc->random_access && basesrc->data.ABI.typefind && size != -1) {
       
  2376     GstCaps *caps;
       
  2377 
       
  2378     caps = gst_type_find_helper (basesrc->srcpad, size);
       
  2379     gst_pad_set_caps (basesrc->srcpad, caps);
       
  2380     gst_caps_unref (caps);
       
  2381   } else {
       
  2382     /* use class or default negotiate function */
       
  2383     if (!gst_base_src_negotiate (basesrc))
       
  2384       goto could_not_negotiate;
       
  2385   }
       
  2386 
       
  2387   return TRUE;
       
  2388 
       
  2389   /* ERROR */
       
  2390 could_not_start:
       
  2391   {
       
  2392     GST_DEBUG_OBJECT (basesrc, "could not start");
       
  2393     /* subclass is supposed to post a message. We don't have to call _stop. */
       
  2394     return FALSE;
       
  2395   }
       
  2396 could_not_negotiate:
       
  2397   {
       
  2398     GST_DEBUG_OBJECT (basesrc, "could not negotiate, stopping");
       
  2399     GST_ELEMENT_ERROR (basesrc, STREAM, FORMAT,
       
  2400         ("Could not negotiate format"), ("Check your filtered caps, if any"));
       
  2401     /* we must call stop */
       
  2402     gst_base_src_stop (basesrc);
       
  2403     return FALSE;
       
  2404   }
       
  2405 }
       
  2406 
       
  2407 static gboolean
       
  2408 gst_base_src_stop (GstBaseSrc * basesrc)
       
  2409 {
       
  2410   GstBaseSrcClass *bclass;
       
  2411   gboolean result = TRUE;
       
  2412 
       
  2413   if (!GST_OBJECT_FLAG_IS_SET (basesrc, GST_BASE_SRC_STARTED))
       
  2414     return TRUE;
       
  2415 
       
  2416   GST_DEBUG_OBJECT (basesrc, "stopping source");
       
  2417 
       
  2418   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  2419   if (bclass->stop)
       
  2420     result = bclass->stop (basesrc);
       
  2421 
       
  2422   if (result)
       
  2423     GST_OBJECT_FLAG_UNSET (basesrc, GST_BASE_SRC_STARTED);
       
  2424 
       
  2425   return result;
       
  2426 }
       
  2427 
       
  2428 /* start or stop flushing dataprocessing 
       
  2429  */
       
  2430 static gboolean
       
  2431 gst_base_src_set_flushing (GstBaseSrc * basesrc,
       
  2432     gboolean flushing, gboolean live_play, gboolean unlock, gboolean * playing)
       
  2433 {
       
  2434   GstBaseSrcClass *bclass;
       
  2435 
       
  2436   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  2437 
       
  2438   if (flushing && unlock) {
       
  2439     /* unlock any subclasses, we need to do this before grabbing the
       
  2440      * LIVE_LOCK since we hold this lock before going into ::create. We pass an
       
  2441      * unlock to the params because of backwards compat (see seek handler)*/
       
  2442     if (bclass->unlock)
       
  2443       bclass->unlock (basesrc);
       
  2444   }
       
  2445 
       
  2446   /* the live lock is released when we are blocked, waiting for playing or
       
  2447    * when we sync to the clock. */
       
  2448   GST_LIVE_LOCK (basesrc);
       
  2449   if (playing)
       
  2450     *playing = basesrc->live_running;
       
  2451   basesrc->priv->flushing = flushing;
       
  2452   if (flushing) {
       
  2453     /* if we are locked in the live lock, signal it to make it flush */
       
  2454     basesrc->live_running = TRUE;
       
  2455     /* clear pending EOS if any */
       
  2456     basesrc->priv->pending_eos = FALSE;
       
  2457 
       
  2458     /* step 1, now that we have the LIVE lock, clear our unlock request */
       
  2459     if (bclass->unlock_stop)
       
  2460       bclass->unlock_stop (basesrc);
       
  2461 
       
  2462     /* step 2, unblock clock sync (if any) or any other blocking thing */
       
  2463     if (basesrc->clock_id)
       
  2464       gst_clock_id_unschedule (basesrc->clock_id);
       
  2465   } else {
       
  2466     /* signal the live source that it can start playing */
       
  2467     basesrc->live_running = live_play;
       
  2468   }
       
  2469   GST_LIVE_SIGNAL (basesrc);
       
  2470   GST_LIVE_UNLOCK (basesrc);
       
  2471 
       
  2472   return TRUE;
       
  2473 }
       
  2474 
       
  2475 /* the purpose of this function is to make sure that a live source blocks in the
       
  2476  * LIVE lock or leaves the LIVE lock and continues playing. */
       
  2477 static gboolean
       
  2478 gst_base_src_set_playing (GstBaseSrc * basesrc, gboolean live_play)
       
  2479 {
       
  2480   GstBaseSrcClass *bclass;
       
  2481 
       
  2482   bclass = GST_BASE_SRC_GET_CLASS (basesrc);
       
  2483 
       
  2484   /* unlock subclasses locked in ::create, we only do this when we stop playing. */
       
  2485   if (!live_play) {
       
  2486     GST_DEBUG_OBJECT (basesrc, "unlock");
       
  2487     if (bclass->unlock)
       
  2488       bclass->unlock (basesrc);
       
  2489   }
       
  2490 
       
  2491   /* we are now able to grab the LIVE lock, when we get it, we can be
       
  2492    * waiting for PLAYING while blocked in the LIVE cond or we can be waiting
       
  2493    * for the clock. */
       
  2494   GST_LIVE_LOCK (basesrc);
       
  2495   GST_DEBUG_OBJECT (basesrc, "unschedule clock");
       
  2496 
       
  2497   /* unblock clock sync (if any) */
       
  2498   if (basesrc->clock_id)
       
  2499     gst_clock_id_unschedule (basesrc->clock_id);
       
  2500 
       
  2501   /* configure what to do when we get to the LIVE lock. */
       
  2502   GST_DEBUG_OBJECT (basesrc, "live running %d", live_play);
       
  2503   basesrc->live_running = live_play;
       
  2504 
       
  2505   if (live_play) {
       
  2506     gboolean start;
       
  2507 
       
  2508     /* clear our unlock request when going to PLAYING */
       
  2509     GST_DEBUG_OBJECT (basesrc, "unlock stop");
       
  2510     if (bclass->unlock_stop)
       
  2511       bclass->unlock_stop (basesrc);
       
  2512 
       
  2513     /* for live sources we restart the timestamp correction */
       
  2514     basesrc->priv->latency = -1;
       
  2515     /* have to restart the task in case it stopped because of the unlock when
       
  2516      * we went to PAUSED. Only do this if we operating in push mode. */
       
  2517     GST_OBJECT_LOCK (basesrc->srcpad);
       
  2518     start = (GST_PAD_ACTIVATE_MODE (basesrc->srcpad) == GST_ACTIVATE_PUSH);
       
  2519     GST_OBJECT_UNLOCK (basesrc->srcpad);
       
  2520     if (start)
       
  2521       gst_pad_start_task (basesrc->srcpad, (GstTaskFunction) gst_base_src_loop,
       
  2522           basesrc->srcpad);
       
  2523     GST_DEBUG_OBJECT (basesrc, "signal");
       
  2524     GST_LIVE_SIGNAL (basesrc);
       
  2525   }
       
  2526   GST_LIVE_UNLOCK (basesrc);
       
  2527 
       
  2528   return TRUE;
       
  2529 }
       
  2530 
       
  2531 static gboolean
       
  2532 gst_base_src_activate_push (GstPad * pad, gboolean active)
       
  2533 {
       
  2534   GstBaseSrc *basesrc;
       
  2535   GstEvent *event;
       
  2536 
       
  2537   basesrc = GST_BASE_SRC (GST_OBJECT_PARENT (pad));
       
  2538 
       
  2539   /* prepare subclass first */
       
  2540   if (active) {
       
  2541     GST_DEBUG_OBJECT (basesrc, "Activating in push mode");
       
  2542 
       
  2543     if (G_UNLIKELY (!basesrc->can_activate_push))
       
  2544       goto no_push_activation;
       
  2545 
       
  2546     if (G_UNLIKELY (!gst_base_src_start (basesrc)))
       
  2547       goto error_start;
       
  2548 
       
  2549     basesrc->priv->last_sent_eos = FALSE;
       
  2550     basesrc->priv->discont = TRUE;
       
  2551     gst_base_src_set_flushing (basesrc, FALSE, FALSE, FALSE, NULL);
       
  2552 
       
  2553     /* do initial seek, which will start the task */
       
  2554     GST_OBJECT_LOCK (basesrc);
       
  2555     event = basesrc->data.ABI.pending_seek;
       
  2556     basesrc->data.ABI.pending_seek = NULL;
       
  2557     GST_OBJECT_UNLOCK (basesrc);
       
  2558 
       
  2559     /* no need to unlock anything, the task is certainly
       
  2560      * not running here. The perform seek code will start the task when
       
  2561      * finished. */
       
  2562     if (G_UNLIKELY (!gst_base_src_perform_seek (basesrc, event, FALSE)))
       
  2563       goto seek_failed;
       
  2564 
       
  2565     if (event)
       
  2566       gst_event_unref (event);
       
  2567   } else {
       
  2568     GST_DEBUG_OBJECT (basesrc, "Deactivating in push mode");
       
  2569     /* flush all */
       
  2570     gst_base_src_set_flushing (basesrc, TRUE, FALSE, TRUE, NULL);
       
  2571     /* stop the task */
       
  2572     gst_pad_stop_task (pad);
       
  2573     /* now we can stop the source */
       
  2574     if (G_UNLIKELY (!gst_base_src_stop (basesrc)))
       
  2575       goto error_stop;
       
  2576   }
       
  2577   return TRUE;
       
  2578 
       
  2579   /* ERRORS */
       
  2580 no_push_activation:
       
  2581   {
       
  2582     GST_WARNING_OBJECT (basesrc, "Subclass disabled push-mode activation");
       
  2583     return FALSE;
       
  2584   }
       
  2585 error_start:
       
  2586   {
       
  2587     GST_WARNING_OBJECT (basesrc, "Failed to start in push mode");
       
  2588     return FALSE;
       
  2589   }
       
  2590 seek_failed:
       
  2591   {
       
  2592     GST_ERROR_OBJECT (basesrc, "Failed to perform initial seek");
       
  2593     gst_base_src_stop (basesrc);
       
  2594     if (event)
       
  2595       gst_event_unref (event);
       
  2596     return FALSE;
       
  2597   }
       
  2598 error_stop:
       
  2599   {
       
  2600     GST_DEBUG_OBJECT (basesrc, "Failed to stop in push mode");
       
  2601     return FALSE;
       
  2602   }
       
  2603 }
       
  2604 
       
  2605 static gboolean
       
  2606 gst_base_src_activate_pull (GstPad * pad, gboolean active)
       
  2607 {
       
  2608   GstBaseSrc *basesrc;
       
  2609 
       
  2610   basesrc = GST_BASE_SRC (GST_OBJECT_PARENT (pad));
       
  2611 
       
  2612   /* prepare subclass first */
       
  2613   if (active) {
       
  2614     GST_DEBUG_OBJECT (basesrc, "Activating in pull mode");
       
  2615     if (G_UNLIKELY (!gst_base_src_start (basesrc)))
       
  2616       goto error_start;
       
  2617 
       
  2618     /* if not random_access, we cannot operate in pull mode for now */
       
  2619     if (G_UNLIKELY (!gst_base_src_check_get_range (basesrc)))
       
  2620       goto no_get_range;
       
  2621 
       
  2622     /* stop flushing now but for live sources, still block in the LIVE lock when
       
  2623      * we are not yet PLAYING */
       
  2624     gst_base_src_set_flushing (basesrc, FALSE, FALSE, FALSE, NULL);
       
  2625   } else {
       
  2626     GST_DEBUG_OBJECT (basesrc, "Deactivating in pull mode");
       
  2627     /* flush all, there is no task to stop */
       
  2628     gst_base_src_set_flushing (basesrc, TRUE, FALSE, TRUE, NULL);
       
  2629 
       
  2630     /* don't send EOS when going from PAUSED => READY when in pull mode */
       
  2631     basesrc->priv->last_sent_eos = TRUE;
       
  2632 
       
  2633     if (G_UNLIKELY (!gst_base_src_stop (basesrc)))
       
  2634       goto error_stop;
       
  2635   }
       
  2636   return TRUE;
       
  2637 
       
  2638   /* ERRORS */
       
  2639 error_start:
       
  2640   {
       
  2641     GST_ERROR_OBJECT (basesrc, "Failed to start in pull mode");
       
  2642     return FALSE;
       
  2643   }
       
  2644 no_get_range:
       
  2645   {
       
  2646     GST_ERROR_OBJECT (basesrc, "Cannot operate in pull mode, stopping");
       
  2647     gst_base_src_stop (basesrc);
       
  2648     return FALSE;
       
  2649   }
       
  2650 error_stop:
       
  2651   {
       
  2652     GST_ERROR_OBJECT (basesrc, "Failed to stop in pull mode");
       
  2653     return FALSE;
       
  2654   }
       
  2655 }
       
  2656 
       
  2657 static GstStateChangeReturn
       
  2658 gst_base_src_change_state (GstElement * element, GstStateChange transition)
       
  2659 {
       
  2660   GstBaseSrc *basesrc;
       
  2661   GstStateChangeReturn result;
       
  2662   gboolean no_preroll = FALSE;
       
  2663 
       
  2664   basesrc = GST_BASE_SRC (element);
       
  2665 
       
  2666   switch (transition) {
       
  2667     case GST_STATE_CHANGE_NULL_TO_READY:
       
  2668       break;
       
  2669     case GST_STATE_CHANGE_READY_TO_PAUSED:
       
  2670       no_preroll = gst_base_src_is_live (basesrc);
       
  2671       break;
       
  2672     case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
       
  2673       GST_DEBUG_OBJECT (basesrc, "PAUSED->PLAYING");
       
  2674       if (gst_base_src_is_live (basesrc)) {
       
  2675         /* now we can start playback */
       
  2676         gst_base_src_set_playing (basesrc, TRUE);
       
  2677       }
       
  2678       break;
       
  2679     default:
       
  2680       break;
       
  2681   }
       
  2682 
       
  2683   if ((result =
       
  2684           GST_ELEMENT_CLASS (parent_class)->change_state (element,
       
  2685               transition)) == GST_STATE_CHANGE_FAILURE)
       
  2686     goto failure;
       
  2687 
       
  2688   switch (transition) {
       
  2689     case GST_STATE_CHANGE_PLAYING_TO_PAUSED:
       
  2690       GST_DEBUG_OBJECT (basesrc, "PLAYING->PAUSED");
       
  2691       if (gst_base_src_is_live (basesrc)) {
       
  2692         /* make sure we block in the live lock in PAUSED */
       
  2693         gst_base_src_set_playing (basesrc, FALSE);
       
  2694         no_preroll = TRUE;
       
  2695       }
       
  2696       break;
       
  2697     case GST_STATE_CHANGE_PAUSED_TO_READY:
       
  2698     {
       
  2699       GstEvent **event_p;
       
  2700 
       
  2701       /* we don't need to unblock anything here, the pad deactivation code
       
  2702        * already did this */
       
  2703 
       
  2704       /* FIXME, deprecate this behaviour, it is very dangerous.
       
  2705        * the prefered way of sending EOS downstream is by sending
       
  2706        * the EOS event to the element */
       
  2707       if (!basesrc->priv->last_sent_eos) {
       
  2708         GST_DEBUG_OBJECT (basesrc, "Sending EOS event");
       
  2709         gst_pad_push_event (basesrc->srcpad, gst_event_new_eos ());
       
  2710         basesrc->priv->last_sent_eos = TRUE;
       
  2711       }
       
  2712       basesrc->priv->pending_eos = FALSE;
       
  2713       event_p = &basesrc->data.ABI.pending_seek;
       
  2714       gst_event_replace (event_p, NULL);
       
  2715       event_p = &basesrc->priv->close_segment;
       
  2716       gst_event_replace (event_p, NULL);
       
  2717       event_p = &basesrc->priv->start_segment;
       
  2718       gst_event_replace (event_p, NULL);
       
  2719       break;
       
  2720     }
       
  2721     case GST_STATE_CHANGE_READY_TO_NULL:
       
  2722       break;
       
  2723     default:
       
  2724       break;
       
  2725   }
       
  2726 
       
  2727   if (no_preroll && result == GST_STATE_CHANGE_SUCCESS)
       
  2728     result = GST_STATE_CHANGE_NO_PREROLL;
       
  2729 
       
  2730   return result;
       
  2731 
       
  2732   /* ERRORS */
       
  2733 failure:
       
  2734   {
       
  2735     GST_DEBUG_OBJECT (basesrc, "parent failed state change");
       
  2736     return result;
       
  2737   }
       
  2738 }