summaryrefslogtreecommitdiff
path: root/gst
diff options
context:
space:
mode:
authorEdward Hervey <edward@centricular.com>2016-07-13 11:02:23 +0200
committerEdward Hervey <bilboed@bilboed.com>2016-08-03 17:15:41 +0200
commit51c5ff45de81e96dbace2a872505274d7de0341c (patch)
tree2ed8feac75199cc17030c23eb000f9b64faae560 /gst
parente2b98a7721c7c81fd08813d1c575fc4ad81df38e (diff)
downloadgstreamer-plugins-bad-51c5ff45de81e96dbace2a872505274d7de0341c.tar.gz
tsdemux: Fix draining on wrong programs
When draining a program, we might send a newsegment event on the pads that are going to be removed (and then the pending data). In order to do that, calculate_and_push_newsegment() needs to know what list of streams it should take into account (instead of blindly using the current one). All callers to calculate_and_push_newsegment() and push_pending_data() can now specify the program on which to act (or NULL for the default one).
Diffstat (limited to 'gst')
-rw-r--r--gst/mpegtsdemux/tsdemux.c34
1 files changed, 21 insertions, 13 deletions
diff --git a/gst/mpegtsdemux/tsdemux.c b/gst/mpegtsdemux/tsdemux.c
index a6d0fab0c..7a396cd87 100644
--- a/gst/mpegtsdemux/tsdemux.c
+++ b/gst/mpegtsdemux/tsdemux.c
@@ -305,7 +305,8 @@ static void gst_ts_demux_get_property (GObject * object, guint prop_id,
GValue * value, GParamSpec * pspec);
static void gst_ts_demux_flush_streams (GstTSDemux * tsdemux, gboolean hard);
static GstFlowReturn
-gst_ts_demux_push_pending_data (GstTSDemux * demux, TSDemuxStream * stream);
+gst_ts_demux_push_pending_data (GstTSDemux * demux, TSDemuxStream * stream,
+ MpegTSBaseProgram * program);
static void gst_ts_demux_stream_flush (TSDemuxStream * stream,
GstTSDemux * demux, gboolean hard);
@@ -972,7 +973,7 @@ push_event (MpegTSBase * base, GstEvent * event)
/* If we are pushing out EOS, flush out pending data first */
if (GST_EVENT_TYPE (event) == GST_EVENT_EOS &&
gst_pad_is_active (stream->pad))
- gst_ts_demux_push_pending_data (demux, stream);
+ gst_ts_demux_push_pending_data (demux, stream, NULL);
gst_event_ref (event);
gst_pad_push_event (stream->pad, event);
@@ -1683,7 +1684,7 @@ gst_ts_demux_stream_removed (MpegTSBase * base, MpegTSBaseStream * bstream)
if (gst_pad_is_active (stream->pad)) {
/* Flush out all data */
GST_DEBUG_OBJECT (stream->pad, "Flushing out pending data");
- gst_ts_demux_push_pending_data ((GstTSDemux *) base, stream);
+ gst_ts_demux_push_pending_data ((GstTSDemux *) base, stream, NULL);
GST_DEBUG_OBJECT (stream->pad, "Pushing out EOS");
gst_pad_push_event (stream->pad, gst_event_new_eos ());
@@ -1831,7 +1832,8 @@ gst_ts_demux_program_started (MpegTSBase * base, MpegTSBaseProgram * program)
for (tmp = demux->previous_program->stream_list; tmp; tmp = tmp->next) {
TSDemuxStream *stream = (TSDemuxStream *) tmp->data;
if (stream->pad)
- gst_ts_demux_push_pending_data (demux, stream);
+ gst_ts_demux_push_pending_data (demux, stream,
+ demux->previous_program);
}
}
@@ -2231,7 +2233,8 @@ gst_ts_demux_queue_data (GstTSDemux * demux, TSDemuxStream * stream,
}
static void
-calculate_and_push_newsegment (GstTSDemux * demux, TSDemuxStream * stream)
+calculate_and_push_newsegment (GstTSDemux * demux, TSDemuxStream * stream,
+ MpegTSBaseProgram * target_program)
{
MpegTSBase *base = (MpegTSBase *) demux;
GstClockTime lowest_pts = GST_CLOCK_TIME_NONE;
@@ -2240,12 +2243,15 @@ calculate_and_push_newsegment (GstTSDemux * demux, TSDemuxStream * stream)
GST_DEBUG ("Creating new newsegment for stream %p", stream);
+ if (target_program == NULL)
+ target_program = demux->program;
+
/* Speedup : if we don't need to calculate anything, go straight to pushing */
if (demux->segment_event)
goto push_new_segment;
/* Calculate the 'new_start' value, used for newsegment */
- for (tmp = demux->program->stream_list; tmp; tmp = tmp->next) {
+ for (tmp = target_program->stream_list; tmp; tmp = tmp->next) {
TSDemuxStream *pstream = (TSDemuxStream *) tmp->data;
if (GST_CLOCK_TIME_IS_VALID (pstream->first_pts)) {
@@ -2294,7 +2300,7 @@ calculate_and_push_newsegment (GstTSDemux * demux, TSDemuxStream * stream)
}
push_new_segment:
- for (tmp = demux->program->stream_list; tmp; tmp = tmp->next) {
+ for (tmp = target_program->stream_list; tmp; tmp = tmp->next) {
stream = (TSDemuxStream *) tmp->data;
if (stream->pad == NULL)
continue;
@@ -2369,7 +2375,7 @@ gst_ts_demux_check_and_sync_streams (GstTSDemux * demux, GstClockTime time)
"Stream needs update. Pushing GAP event to TS %" GST_TIME_FORMAT,
GST_TIME_ARGS (time));
if (G_UNLIKELY (ps->need_newsegment))
- calculate_and_push_newsegment (demux, ps);
+ calculate_and_push_newsegment (demux, ps, NULL);
/* Now send gap event */
gst_pad_push_event (ps->pad, gst_event_new_gap (time, 0));
@@ -2477,13 +2483,15 @@ error:
}
static GstFlowReturn
-gst_ts_demux_push_pending_data (GstTSDemux * demux, TSDemuxStream * stream)
+gst_ts_demux_push_pending_data (GstTSDemux * demux, TSDemuxStream * stream,
+ MpegTSBaseProgram * target_program)
{
GstFlowReturn res = GST_FLOW_OK;
MpegTSBaseStream *bs = (MpegTSBaseStream *) stream;
GstBuffer *buffer = NULL;
GstBufferList *buffer_list = NULL;
+
GST_DEBUG_OBJECT (stream->pad,
"stream:%p, pid:0x%04x stream_type:%d state:%d", stream, bs->pid,
bs->stream_type, stream->state);
@@ -2597,7 +2605,7 @@ gst_ts_demux_push_pending_data (GstTSDemux * demux, TSDemuxStream * stream)
}
if (G_UNLIKELY (stream->need_newsegment))
- calculate_and_push_newsegment (demux, stream);
+ calculate_and_push_newsegment (demux, stream, target_program);
/* FIXME : Push pending buffers if any */
if (G_UNLIKELY (stream->pending)) {
@@ -2731,7 +2739,7 @@ gst_ts_demux_handle_packet (GstTSDemux * demux, TSDemuxStream * stream,
if (G_UNLIKELY (packet->payload_unit_start_indicator) &&
FLAGS_HAS_PAYLOAD (packet->scram_afc_cc))
/* Flush previous data */
- res = gst_ts_demux_push_pending_data (demux, stream);
+ res = gst_ts_demux_push_pending_data (demux, stream, NULL);
if (packet->payload && (res == GST_FLOW_OK || res == GST_FLOW_NOT_LINKED)
&& stream->pad) {
@@ -2741,7 +2749,7 @@ gst_ts_demux_handle_packet (GstTSDemux * demux, TSDemuxStream * stream,
/* Finally check if the data we queued completes a packet */
if (stream->expected_size && stream->current_size == stream->expected_size) {
GST_LOG ("pushing complete packet");
- res = gst_ts_demux_push_pending_data (demux, stream);
+ res = gst_ts_demux_push_pending_data (demux, stream, NULL);
}
}
@@ -2789,7 +2797,7 @@ gst_ts_demux_drain (MpegTSBase * base)
for (tmp = demux->program->stream_list; tmp; tmp = tmp->next) {
TSDemuxStream *stream = (TSDemuxStream *) tmp->data;
if (stream->pad) {
- res = gst_ts_demux_push_pending_data (demux, stream);
+ res = gst_ts_demux_push_pending_data (demux, stream, NULL);
if (G_UNLIKELY (res != GST_FLOW_OK))
break;
}