From: <tp...@ke...> - 2007-05-16 19:08:07
|
CVS Root: /cvs/gstreamer Module: gst-plugins-ugly Changes by: tpm Date: Wed May 16 2007 19:07:58 UTC Log message: * gst/realmedia/rmdemux.c: (gst_rmdemux_init), (gst_rmdemux_sink_event), (gst_rmdemux_perform_seek), (gst_rmdemux_reset), (gst_rmdemux_chain), (gst_rmdemux_add_stream), (gst_rmdemux_parse_packet): * gst/realmedia/rmdemux.h: Remember first timestamp encountered in stream and re-timestamp stream to start from zero (fixes #397219); only send one newsegment event, not two; when seeking, send newsegment events from the streaming thread and not from the seeking thread. Modified files: . : ChangeLog gst/realmedia : rmdemux.c rmdemux.h Links: http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-ugly/ChangeLog.diff?r1=1.2198&r2=1.2199 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-ugly/gst/realmedia/rmdemux.c.diff?r1=1.87&r2=1.88 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-ugly/gst/realmedia/rmdemux.h.diff?r1=1.17&r2=1.18 ====Begin Diffs==== Index: ChangeLog =================================================================== RCS file: /cvs/gstreamer/gst-plugins-ugly/ChangeLog,v retrieving revision 1.2198 retrieving revision 1.2199 diff -u -d -r1.2198 -r1.2199 --- ChangeLog 16 May 2007 12:48:39 -0000 1.2198 +++ ChangeLog 16 May 2007 19:07:45 -0000 1.2199 @@ -1,5 +1,17 @@ 2007-05-16 Tim-Philipp Müller <tim at centricular dot net> + * gst/realmedia/rmdemux.c: (gst_rmdemux_init), + (gst_rmdemux_sink_event), (gst_rmdemux_perform_seek), + (gst_rmdemux_reset), (gst_rmdemux_chain), (gst_rmdemux_add_stream), + (gst_rmdemux_parse_packet): + * gst/realmedia/rmdemux.h: + Remember first timestamp encountered in stream and re-timestamp + stream to start from zero (fixes #397219); only send one newsegment + event, not two; when seeking, send newsegment events from the + streaming thread and not from the seeking thread. + +2007-05-16 Tim-Philipp Müller <tim at centricular dot net> Based on patch by: Mark Nauwelaerts <manauw skynet be> * gst/mpegstream/gstdvddemux.c: (gst_dvd_demux_process_event): Index: rmdemux.c RCS file: /cvs/gstreamer/gst-plugins-ugly/gst/realmedia/rmdemux.c,v retrieving revision 1.87 retrieving revision 1.88 diff -u -d -r1.87 -r1.88 --- rmdemux.c 12 Apr 2007 10:10:22 -0000 1.87 +++ rmdemux.c 16 May 2007 19:07:45 -0000 1.88 @@ -1,4 +1,4 @@ -/* GStreamer +/* GStreamer RealMedia demuxer * Copyright (C) <1999> Erik Walthinsen <om...@cs...> * Copyright (C) <2003> David A. Schleef <ds...@sc...> * Copyright (C) <2004> Stephane Loeuillet <gst...@le...> @@ -77,6 +77,8 @@ gboolean needs_descrambling; guint subpackets_needed; /* subpackets needed for descrambling */ GPtrArray *subpackets; /* array containing subpacket GstBuffers */ + GstTagList *pending_tags; }; struct _GstRMDemuxIndex @@ -244,29 +246,31 @@ gst_element_add_pad (GST_ELEMENT (rmdemux), rmdemux->sinkpad); rmdemux->adapter = gst_adapter_new (); + rmdemux->first_ts = GST_CLOCK_TIME_NONE; + rmdemux->need_newsegment = TRUE; } static gboolean gst_rmdemux_sink_event (GstPad * pad, GstEvent * event) { - gboolean ret = TRUE; + GstRMDemux *rmdemux; + gboolean ret; -#ifndef GST_DISABLE_GST_DEBUG - GstRMDemux *rmdemux = GST_RMDEMUX (GST_PAD_PARENT (pad)); -#endif + rmdemux = GST_RMDEMUX (gst_pad_get_parent (pad)); + GST_LOG_OBJECT (pad, "%s event", GST_EVENT_TYPE_NAME (event)); switch (GST_EVENT_TYPE (event)) { case GST_EVENT_NEWSEGMENT: - GST_LOG_OBJECT (rmdemux, "Event on sink: NEWSEGMENT"); gst_event_unref (event); + ret = TRUE; break; default: - GST_LOG_OBJECT (rmdemux, "Event on sink: type=%d", - GST_EVENT_TYPE (event)); ret = gst_pad_event_default (pad, event); } + gst_object_unref (rmdemux); return ret; @@ -562,23 +566,14 @@ /* now we have a new position, prepare for streaming again */ { - GstEvent *event; - /* Reset the demuxer state */ rmdemux->state = RMDEMUX_STATE_DATA_PACKET; if (flush) gst_rmdemux_send_event (rmdemux, gst_event_new_flush_stop ()); - /* create the discont event we are going to send out */ - event = gst_event_new_new_segment (FALSE, rmdemux->segment.rate, - rmdemux->segment.format, rmdemux->segment.start, - rmdemux->segment.stop, rmdemux->segment.time); - GST_DEBUG_OBJECT (rmdemux, - "sending NEWSEGMENT event to all src pads with segment.start= %" - GST_TIME_FORMAT, GST_TIME_ARGS (rmdemux->segment.start)); - gst_rmdemux_send_event (rmdemux, event); + /* must send newsegment event from streaming thread, so just set flag */ + rmdemux->need_newsegment = TRUE; /* notify start of new segment */ if (rmdemux->segment.flags & GST_SEEK_FLAG_SEGMENT) { @@ -586,6 +581,7 @@ gst_message_new_segment_start (GST_OBJECT_CAST (rmdemux), GST_FORMAT_TIME, rmdemux->segment.last_stop)); } /* restart our task since it might have been stopped when we did the * flush. */ gst_pad_start_task (rmdemux->sinkpad, (GstTaskFunction) gst_rmdemux_loop, @@ -685,6 +681,8 @@ gst_rmdemux_stream_clear_cached_subpackets (rmdemux, stream); gst_element_remove_pad (GST_ELEMENT (rmdemux), stream->pad); + if (stream->pending_tags) + gst_tag_list_free (stream->pending_tags); if (stream->subpackets) g_ptr_array_free (stream->subpackets, TRUE); g_free (stream->index); @@ -700,6 +698,8 @@ rmdemux->have_pads = FALSE; gst_segment_init (&rmdemux->segment, GST_FORMAT_UNDEFINED); static GstStateChangeReturn @@ -1084,18 +1084,14 @@ { /* If we haven't already done so then signal there are no more pads */ if (!rmdemux->have_pads) { + GST_LOG_OBJECT (rmdemux, "no more pads"); gst_element_no_more_pads (GST_ELEMENT (rmdemux)); rmdemux->have_pads = TRUE; - GST_LOG_OBJECT (rmdemux, "no more pads."); - gst_rmdemux_send_event (rmdemux, - gst_event_new_new_segment (FALSE, 1.0, GST_FORMAT_TIME, - (gint64) 0, (gint64) - 1, 0)); } /* The actual header is only 8 bytes */ rmdemux->size = DATA_SIZE; - GST_DEBUG_OBJECT (rmdemux, "data available %d", + GST_LOG_OBJECT (rmdemux, "data available %d", gst_adapter_available (rmdemux->adapter)); if (gst_adapter_available (rmdemux->adapter) < rmdemux->size) goto unlock; @@ -1444,16 +1440,11 @@ gst_pad_set_active (stream->pad, TRUE); gst_element_add_pad (GST_ELEMENT_CAST (rmdemux), stream->pad); - gst_pad_push_event (stream->pad, - gst_event_new_new_segment (FALSE, 1.0, GST_FORMAT_TIME, (gint64) 0, - (gint64) - 1, 0)); - if (codec_name && codec_tag) { - GstTagList *tags = NULL; - tags = gst_tag_list_new (); - gst_tag_list_add (tags, GST_TAG_MERGE_KEEP, codec_tag, codec_name, NULL); - gst_element_found_tags_for_pad (GST_ELEMENT (rmdemux), stream->pad, tags); + /* save for later, we must send the tags after the newsegment event */ + if (codec_name != NULL && codec_tag != NULL) { + stream->pending_tags = gst_tag_list_new (); + gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_KEEP, + codec_tag, codec_name, NULL); @@ -1988,6 +1979,33 @@ if (!stream || !stream->pad) goto unknown_stream; + if (rmdemux->first_ts == GST_CLOCK_TIME_NONE) { + GST_DEBUG_OBJECT (rmdemux, "First timestamp: %" GST_TIME_FORMAT, + GST_TIME_ARGS (timestamp)); + rmdemux->first_ts = timestamp; + } + if (rmdemux->need_newsegment) { + GstEvent *event; + event = gst_event_new_new_segment (FALSE, rmdemux->segment.rate, + rmdemux->segment.format, rmdemux->segment.start, + rmdemux->segment.stop, rmdemux->segment.time); + GST_DEBUG_OBJECT (rmdemux, "sending NEWSEGMENT event, segment.start= %" + GST_TIME_FORMAT, GST_TIME_ARGS (rmdemux->segment.start)); + gst_rmdemux_send_event (rmdemux, event); + rmdemux->need_newsegment = FALSE; + if (stream->pending_tags != NULL) { + GST_LOG_OBJECT (stream->pad, "tags %" GST_PTR_FORMAT, stream->pending_tags); + gst_element_found_tags_for_pad (GST_ELEMENT_CAST (rmdemux), stream->pad, + stream->pending_tags); + stream->pending_tags = NULL; if ((rmdemux->offset + packet_size) <= stream->seek_offset) { GST_DEBUG_OBJECT (rmdemux, "Stream %d is skipping: seek_offset=%d, offset=%d, packet_size=%u", @@ -2004,7 +2022,7 @@ goto alloc_failed; memcpy (GST_BUFFER_DATA (buffer), (guint8 *) data, packet_size); - GST_BUFFER_TIMESTAMP (buffer) = timestamp; + GST_BUFFER_TIMESTAMP (buffer) = timestamp - rmdemux->first_ts; if (stream->needs_descrambling) { ret = gst_rmdemux_handle_scrambled_packet (rmdemux, stream, buffer, key); Index: rmdemux.h RCS file: /cvs/gstreamer/gst-plugins-ugly/gst/realmedia/rmdemux.h,v retrieving revision 1.17 retrieving revision 1.18 diff -u -d -r1.17 -r1.18 --- rmdemux.h 12 Apr 2007 10:10:22 -0000 1.17 +++ rmdemux.h 16 May 2007 19:07:45 -0000 1.18 * * This library is free software; you can redistribute it and/or @@ -106,9 +106,15 @@ gboolean segment_running; gboolean running; + /* Whether we need to send a newsegment event */ + gboolean need_newsegment; /* Current timestamp */ GstClockTime cur_timestamp; + /* First timestamp */ + GstClockTime first_ts; int n_chunks; int chunk_index; |