mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-26 19:51:11 +00:00
hlsdemux2: Mark locations where partial segments need handling
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/3883>
This commit is contained in:
parent
cfc62a69f7
commit
92e849070f
5 changed files with 33 additions and 5 deletions
|
@ -974,6 +974,7 @@ out:
|
||||||
GST_STIME_ARGS (current_segment->stream_time +
|
GST_STIME_ARGS (current_segment->stream_time +
|
||||||
current_segment->duration));
|
current_segment->duration));
|
||||||
|
|
||||||
|
/* FIXME: Could seek to an INDEPENDENT partial segment in LL-HLS */
|
||||||
candidate_segment =
|
candidate_segment =
|
||||||
gst_hls_media_playlist_seek (hls_stream->playlist, TRUE,
|
gst_hls_media_playlist_seek (hls_stream->playlist, TRUE,
|
||||||
GST_SEEK_FLAG_SNAP_NEAREST, low_stream_time);
|
GST_SEEK_FLAG_SNAP_NEAREST, low_stream_time);
|
||||||
|
|
|
@ -514,6 +514,7 @@ gst_hls_demux_stream_seek (GstAdaptiveDemux2Stream * stream, gboolean forward,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* FIXME: Allow jumping to partial segments in LL-HLS? */
|
||||||
new_position =
|
new_position =
|
||||||
gst_hls_media_playlist_seek (hls_stream->playlist, forward, flags, ts);
|
gst_hls_media_playlist_seek (hls_stream->playlist, forward, flags, ts);
|
||||||
if (new_position) {
|
if (new_position) {
|
||||||
|
@ -1350,6 +1351,7 @@ gst_hlsdemux_handle_internal_time (GstHLSDemux * demux,
|
||||||
GST_DEBUG_OBJECT (hls_stream,
|
GST_DEBUG_OBJECT (hls_stream,
|
||||||
"Trying to seek to the correct segment for %" GST_STIME_FORMAT,
|
"Trying to seek to the correct segment for %" GST_STIME_FORMAT,
|
||||||
GST_STIME_ARGS (current_stream_time));
|
GST_STIME_ARGS (current_stream_time));
|
||||||
|
/* FIXME: Allow jumping to partial segments in LL-HLS */
|
||||||
actual_segment =
|
actual_segment =
|
||||||
gst_hls_media_playlist_seek (hls_stream->playlist, TRUE,
|
gst_hls_media_playlist_seek (hls_stream->playlist, TRUE,
|
||||||
GST_SEEK_FLAG_SNAP_NEAREST, current_stream_time);
|
GST_SEEK_FLAG_SNAP_NEAREST, current_stream_time);
|
||||||
|
@ -1823,9 +1825,10 @@ gst_hls_demux_stream_advance_fragment (GstAdaptiveDemux2Stream * stream)
|
||||||
GST_STIME_ARGS (hlsdemux_stream->current_segment->stream_time),
|
GST_STIME_ARGS (hlsdemux_stream->current_segment->stream_time),
|
||||||
GST_STR_NULL (hlsdemux_stream->current_segment->uri));
|
GST_STR_NULL (hlsdemux_stream->current_segment->uri));
|
||||||
|
|
||||||
|
/* FIXME: In LL-HLS, handle advancing into the partial-only segment */
|
||||||
new_segment =
|
new_segment =
|
||||||
gst_hls_media_playlist_advance_fragment (hlsdemux_stream->playlist,
|
gst_hls_media_playlist_advance_fragment (hlsdemux_stream->playlist,
|
||||||
hlsdemux_stream->current_segment, stream->demux->segment.rate > 0);
|
hlsdemux_stream->current_segment, stream->demux->segment.rate > 0, FALSE);
|
||||||
if (new_segment) {
|
if (new_segment) {
|
||||||
hlsdemux_stream->reset_pts = FALSE;
|
hlsdemux_stream->reset_pts = FALSE;
|
||||||
if (new_segment->discont_sequence !=
|
if (new_segment->discont_sequence !=
|
||||||
|
@ -2224,6 +2227,11 @@ gst_hls_demux_stream_update_media_playlist (GstHLSDemux * demux,
|
||||||
new_segment =
|
new_segment =
|
||||||
gst_hls_media_playlist_sync_to_segment (new_playlist,
|
gst_hls_media_playlist_sync_to_segment (new_playlist,
|
||||||
stream->current_segment);
|
stream->current_segment);
|
||||||
|
|
||||||
|
/* FIXME: Handle LL-HLS partial segment sync */
|
||||||
|
if (new_segment && new_segment->partial_only)
|
||||||
|
new_segment = NULL;
|
||||||
|
|
||||||
if (new_segment) {
|
if (new_segment) {
|
||||||
if (new_segment->discont_sequence !=
|
if (new_segment->discont_sequence !=
|
||||||
stream->current_segment->discont_sequence)
|
stream->current_segment->discont_sequence)
|
||||||
|
@ -2385,6 +2393,7 @@ gst_hls_demux_stream_update_fragment_info (GstAdaptiveDemux2Stream * stream)
|
||||||
GST_DEBUG_OBJECT (stream,
|
GST_DEBUG_OBJECT (stream,
|
||||||
"Looking up segment for position %" GST_TIME_FORMAT,
|
"Looking up segment for position %" GST_TIME_FORMAT,
|
||||||
GST_TIME_ARGS (stream->current_position));
|
GST_TIME_ARGS (stream->current_position));
|
||||||
|
/* FIXME: Look up partial segments in LL-HLS */
|
||||||
hlsdemux_stream->current_segment =
|
hlsdemux_stream->current_segment =
|
||||||
gst_hls_media_playlist_seek (hlsdemux_stream->playlist, TRUE,
|
gst_hls_media_playlist_seek (hlsdemux_stream->playlist, TRUE,
|
||||||
GST_SEEK_FLAG_SNAP_NEAREST, stream->current_position);
|
GST_SEEK_FLAG_SNAP_NEAREST, stream->current_position);
|
||||||
|
|
|
@ -1218,6 +1218,11 @@ gst_hls_media_playlist_seek (GstHLSMediaPlaylist * playlist, gboolean forward,
|
||||||
for (idx = 0; idx < playlist->segments->len; idx++) {
|
for (idx = 0; idx < playlist->segments->len; idx++) {
|
||||||
GstM3U8MediaSegment *cand = g_ptr_array_index (playlist->segments, idx);
|
GstM3U8MediaSegment *cand = g_ptr_array_index (playlist->segments, idx);
|
||||||
|
|
||||||
|
/* If only full segments was request, skip any segment that
|
||||||
|
* only has EXT-X-PARTs attached */
|
||||||
|
if (cand->partial_only && !(flags & GST_HLS_M3U8_SEEK_FLAG_ALLOW_PARTIAL))
|
||||||
|
continue;
|
||||||
|
|
||||||
if ((forward & snap_after) || snap_nearest) {
|
if ((forward & snap_after) || snap_nearest) {
|
||||||
if (cand->stream_time >= ts ||
|
if (cand->stream_time >= ts ||
|
||||||
(snap_nearest && (ts - cand->stream_time < cand->duration / 2))) {
|
(snap_nearest && (ts - cand->stream_time < cand->duration / 2))) {
|
||||||
|
@ -1736,7 +1741,8 @@ gst_hls_media_playlist_has_next_fragment (GstHLSMediaPlaylist * m3u8,
|
||||||
|
|
||||||
GstM3U8MediaSegment *
|
GstM3U8MediaSegment *
|
||||||
gst_hls_media_playlist_advance_fragment (GstHLSMediaPlaylist * m3u8,
|
gst_hls_media_playlist_advance_fragment (GstHLSMediaPlaylist * m3u8,
|
||||||
GstM3U8MediaSegment * current, gboolean forward)
|
GstM3U8MediaSegment * current, gboolean forward,
|
||||||
|
gboolean allow_partial_only_segment)
|
||||||
{
|
{
|
||||||
GstM3U8MediaSegment *file = NULL;
|
GstM3U8MediaSegment *file = NULL;
|
||||||
guint idx;
|
guint idx;
|
||||||
|
@ -1768,6 +1774,12 @@ gst_hls_media_playlist_advance_fragment (GstHLSMediaPlaylist * m3u8,
|
||||||
idx - 1));
|
idx - 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (file && file->partial_only && !allow_partial_only_segment) {
|
||||||
|
GST_LOG
|
||||||
|
("Ignoring segment with only partials as full segment was requested");
|
||||||
|
file = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
if (file)
|
if (file)
|
||||||
GST_DEBUG ("Advanced to segment sn:%" G_GINT64_FORMAT " dsn:%"
|
GST_DEBUG ("Advanced to segment sn:%" G_GINT64_FORMAT " dsn:%"
|
||||||
G_GINT64_FORMAT, file->sequence, file->discont_sequence);
|
G_GINT64_FORMAT, file->sequence, file->discont_sequence);
|
||||||
|
|
|
@ -65,6 +65,11 @@ typedef enum {
|
||||||
GST_HLS_PLAYLIST_TYPE_VOD,
|
GST_HLS_PLAYLIST_TYPE_VOD,
|
||||||
} GstHLSPlaylistType;
|
} GstHLSPlaylistType;
|
||||||
|
|
||||||
|
/* Extra seek flag extensions for partial segment handling
|
||||||
|
* Values are chosen to avoid collision with the core GST_SEEK_FLAG_*
|
||||||
|
* flags */
|
||||||
|
#define GST_HLS_M3U8_SEEK_FLAG_ALLOW_PARTIAL (1 << 16) /* Allow seeking to a partial segment */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* GstHLSMediaPlaylist:
|
* GstHLSMediaPlaylist:
|
||||||
*
|
*
|
||||||
|
@ -271,7 +276,8 @@ gst_hls_media_playlist_has_next_fragment (GstHLSMediaPlaylist * m3u8,
|
||||||
GstM3U8MediaSegment *
|
GstM3U8MediaSegment *
|
||||||
gst_hls_media_playlist_advance_fragment (GstHLSMediaPlaylist * m3u8,
|
gst_hls_media_playlist_advance_fragment (GstHLSMediaPlaylist * m3u8,
|
||||||
GstM3U8MediaSegment * current,
|
GstM3U8MediaSegment * current,
|
||||||
gboolean forward);
|
gboolean forward,
|
||||||
|
gboolean allow_partial_only_segment);
|
||||||
|
|
||||||
GstM3U8MediaSegment *
|
GstM3U8MediaSegment *
|
||||||
gst_hls_media_playlist_get_starting_segment (GstHLSMediaPlaylist *self);
|
gst_hls_media_playlist_get_starting_segment (GstHLSMediaPlaylist *self);
|
||||||
|
|
|
@ -690,7 +690,7 @@ GST_START_TEST (test_advance_fragment)
|
||||||
gst_m3u8_media_segment_unref (mf);
|
gst_m3u8_media_segment_unref (mf);
|
||||||
|
|
||||||
/* Check next media segments */
|
/* Check next media segments */
|
||||||
mf = gst_hls_media_playlist_advance_fragment (pl, mf, TRUE);
|
mf = gst_hls_media_playlist_advance_fragment (pl, mf, TRUE, FALSE);
|
||||||
fail_unless (mf != NULL);
|
fail_unless (mf != NULL);
|
||||||
assert_equals_int (mf->discont, FALSE);
|
assert_equals_int (mf->discont, FALSE);
|
||||||
assert_equals_string (mf->uri, "http://media.example.com/all.ts");
|
assert_equals_string (mf->uri, "http://media.example.com/all.ts");
|
||||||
|
@ -701,7 +701,7 @@ GST_START_TEST (test_advance_fragment)
|
||||||
gst_m3u8_media_segment_unref (mf);
|
gst_m3u8_media_segment_unref (mf);
|
||||||
|
|
||||||
/* Check next media segments */
|
/* Check next media segments */
|
||||||
mf = gst_hls_media_playlist_advance_fragment (pl, mf, TRUE);
|
mf = gst_hls_media_playlist_advance_fragment (pl, mf, TRUE, FALSE);
|
||||||
assert_equals_int (mf->discont, FALSE);
|
assert_equals_int (mf->discont, FALSE);
|
||||||
assert_equals_string (mf->uri, "http://media.example.com/all.ts");
|
assert_equals_string (mf->uri, "http://media.example.com/all.ts");
|
||||||
assert_equals_uint64 (mf->stream_time, 20 * GST_SECOND);
|
assert_equals_uint64 (mf->stream_time, 20 * GST_SECOND);
|
||||||
|
|
Loading…
Reference in a new issue