From bc509617310d60216e1f1433a13bebe16d4d9d40 Mon Sep 17 00:00:00 2001 From: Sasi Inguva Date: Thu, 9 Nov 2017 16:11:22 -0800 Subject: lavf/mov.c: Parse upto 2 keyframes after the edit list end in mov_fix_index. Partially fixes t/6699. Signed-off-by: Michael Niedermayer --- libavformat/mov.c | 32 +++++++++++++++++++++----------- 1 file changed, 21 insertions(+), 11 deletions(-) (limited to 'libavformat') diff --git a/libavformat/mov.c b/libavformat/mov.c index 5fc597ee26..fd170baa57 100644 --- a/libavformat/mov.c +++ b/libavformat/mov.c @@ -3298,6 +3298,7 @@ static void mov_fix_index(MOVContext *mov, AVStream *st) int packet_skip_samples = 0; MOVIndexRange *current_index_range; int i; + int found_keyframe_after_edit = 0; if (!msc->elst_data || msc->elst_count <= 0 || nb_old <= 0) { return; @@ -3393,6 +3394,7 @@ static void mov_fix_index(MOVContext *mov, AVStream *st) // Iterate over index and arrange it according to edit list edit_list_start_encountered = 0; + found_keyframe_after_edit = 0; for (; current < e_old_end; current++, index++) { // check if frame outside edit list mark it for discard frame_duration = (current + 1 < e_old_end) ? @@ -3505,18 +3507,26 @@ static void mov_fix_index(MOVContext *mov, AVStream *st) } // Break when found first key frame after edit entry completion - if (((curr_cts + frame_duration) >= (edit_list_duration + edit_list_media_time)) && + if ((curr_cts + frame_duration >= (edit_list_duration + edit_list_media_time)) && ((flags & AVINDEX_KEYFRAME) || ((st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO)))) { - - if (ctts_data_old && ctts_sample_old != 0) { - if (add_ctts_entry(&msc->ctts_data, &msc->ctts_count, - &msc->ctts_allocated_size, - ctts_sample_old - edit_list_start_ctts_sample, - ctts_data_old[ctts_index_old].duration) == -1) { - av_log(mov->fc, AV_LOG_ERROR, "Cannot add CTTS entry %"PRId64" - {%"PRId64", %d}\n", - ctts_index_old, ctts_sample_old - edit_list_start_ctts_sample, - ctts_data_old[ctts_index_old].duration); - break; + if (ctts_data_old) { + // If we have CTTS and this is the the first keyframe after edit elist, + // wait for one more, because there might be trailing B-frames after this I-frame + // that do belong to the edit. + if (st->codecpar->codec_type != AVMEDIA_TYPE_AUDIO && found_keyframe_after_edit == 0) { + found_keyframe_after_edit = 1; + continue; + } + if (ctts_sample_old != 0) { + if (add_ctts_entry(&msc->ctts_data, &msc->ctts_count, + &msc->ctts_allocated_size, + ctts_sample_old - edit_list_start_ctts_sample, + ctts_data_old[ctts_index_old].duration) == -1) { + av_log(mov->fc, AV_LOG_ERROR, "Cannot add CTTS entry %"PRId64" - {%"PRId64", %d}\n", + ctts_index_old, ctts_sample_old - edit_list_start_ctts_sample, + ctts_data_old[ctts_index_old].duration); + break; + } } } break; -- cgit v1.2.3